First commit
This commit is contained in:
commit
9a8ad9985d
|
@ -0,0 +1,60 @@
|
||||||
|
# http://www.gnu.org/software/automake
|
||||||
|
|
||||||
|
|
||||||
|
Makefile.in
|
||||||
|
/ar-lib
|
||||||
|
/mdate-sh
|
||||||
|
/py-compile
|
||||||
|
/test-driver
|
||||||
|
/ylwrap
|
||||||
|
.deps/
|
||||||
|
.dirstamp
|
||||||
|
|
||||||
|
# http://www.gnu.org/software/autoconf
|
||||||
|
|
||||||
|
autom4te.cache
|
||||||
|
/autoscan.log
|
||||||
|
/autoscan-*.log
|
||||||
|
/aclocal.m4
|
||||||
|
/compile
|
||||||
|
/config.cache
|
||||||
|
/config.guess
|
||||||
|
/config.h.in
|
||||||
|
/config.log
|
||||||
|
/config.status
|
||||||
|
/config.sub
|
||||||
|
/configure
|
||||||
|
/configure.scan
|
||||||
|
/depcomp
|
||||||
|
/install-sh
|
||||||
|
/missing
|
||||||
|
/stamp-h1
|
||||||
|
|
||||||
|
# https://www.gnu.org/software/libtool/
|
||||||
|
|
||||||
|
/ltmain.sh
|
||||||
|
|
||||||
|
# http://www.gnu.org/software/texinfo
|
||||||
|
|
||||||
|
/texinfo.tex
|
||||||
|
|
||||||
|
# http://www.gnu.org/software/m4/
|
||||||
|
|
||||||
|
m4/libtool.m4
|
||||||
|
m4/ltoptions.m4
|
||||||
|
m4/ltsugar.m4
|
||||||
|
m4/ltversion.m4
|
||||||
|
m4/lt~obsolete.m4
|
||||||
|
|
||||||
|
# Generated Makefile
|
||||||
|
# (meta build system like autotools,
|
||||||
|
# can automatically generate from config.status script
|
||||||
|
# (which is called by configure script))
|
||||||
|
Makefile
|
||||||
|
Footer
|
||||||
|
!wii/Makefile
|
||||||
|
wii/boot.elf
|
||||||
|
wii/boot.dol
|
||||||
|
wii/build
|
||||||
|
/boxscript
|
||||||
|
*.o
|
|
@ -0,0 +1,17 @@
|
||||||
|
{
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Linux",
|
||||||
|
"includePath": [
|
||||||
|
"${workspaceFolder}/**",
|
||||||
|
"/usr/include/SDL2"
|
||||||
|
],
|
||||||
|
"defines": [],
|
||||||
|
"compilerPath": "/usr/bin/gcc",
|
||||||
|
"cStandard": "gnu17",
|
||||||
|
"cppStandard": "gnu++17",
|
||||||
|
"intelliSenseMode": "linux-gcc-x64"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"version": 4
|
||||||
|
}
|
|
@ -0,0 +1,33 @@
|
||||||
|
{
|
||||||
|
// Use IntelliSense to learn about possible attributes.
|
||||||
|
// Hover to view descriptions of existing attributes.
|
||||||
|
// For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
|
||||||
|
"version": "0.2.0",
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "(gdb) Launch",
|
||||||
|
"type": "cppdbg",
|
||||||
|
"request": "launch",
|
||||||
|
"program": "${workspaceFolder}/source/a.out",
|
||||||
|
"args": ["/media/mike/BOOTMII/BoxScript/webide/app.bs"],
|
||||||
|
"stopAtEntry": false,
|
||||||
|
"cwd": "${fileDirname}",
|
||||||
|
"environment": [],
|
||||||
|
"externalConsole": false,
|
||||||
|
"MIMode": "gdb",
|
||||||
|
"setupCommands": [
|
||||||
|
{
|
||||||
|
"description": "Enable pretty-printing for gdb",
|
||||||
|
"text": "-enable-pretty-printing",
|
||||||
|
"ignoreFailures": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"description": "Set Disassembly Flavor to Intel",
|
||||||
|
"text": "-gdb-set disassembly-flavor intel",
|
||||||
|
"ignoreFailures": true
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
||||||
|
]
|
||||||
|
}
|
|
@ -0,0 +1,58 @@
|
||||||
|
{
|
||||||
|
"files.associations": {
|
||||||
|
"*.tcc": "cpp",
|
||||||
|
"string": "cpp",
|
||||||
|
"iostream": "cpp",
|
||||||
|
"vector": "cpp",
|
||||||
|
"array": "cpp",
|
||||||
|
"atomic": "cpp",
|
||||||
|
"bit": "cpp",
|
||||||
|
"cctype": "cpp",
|
||||||
|
"clocale": "cpp",
|
||||||
|
"cmath": "cpp",
|
||||||
|
"cstdarg": "cpp",
|
||||||
|
"cstddef": "cpp",
|
||||||
|
"cstdint": "cpp",
|
||||||
|
"cstdio": "cpp",
|
||||||
|
"cstdlib": "cpp",
|
||||||
|
"cstring": "cpp",
|
||||||
|
"cwchar": "cpp",
|
||||||
|
"cwctype": "cpp",
|
||||||
|
"deque": "cpp",
|
||||||
|
"map": "cpp",
|
||||||
|
"unordered_map": "cpp",
|
||||||
|
"exception": "cpp",
|
||||||
|
"algorithm": "cpp",
|
||||||
|
"functional": "cpp",
|
||||||
|
"iterator": "cpp",
|
||||||
|
"memory": "cpp",
|
||||||
|
"memory_resource": "cpp",
|
||||||
|
"numeric": "cpp",
|
||||||
|
"optional": "cpp",
|
||||||
|
"random": "cpp",
|
||||||
|
"string_view": "cpp",
|
||||||
|
"system_error": "cpp",
|
||||||
|
"tuple": "cpp",
|
||||||
|
"type_traits": "cpp",
|
||||||
|
"utility": "cpp",
|
||||||
|
"fstream": "cpp",
|
||||||
|
"initializer_list": "cpp",
|
||||||
|
"iosfwd": "cpp",
|
||||||
|
"istream": "cpp",
|
||||||
|
"limits": "cpp",
|
||||||
|
"new": "cpp",
|
||||||
|
"ostream": "cpp",
|
||||||
|
"sstream": "cpp",
|
||||||
|
"stdexcept": "cpp",
|
||||||
|
"streambuf": "cpp",
|
||||||
|
"cinttypes": "cpp",
|
||||||
|
"typeinfo": "cpp",
|
||||||
|
"chrono": "cpp",
|
||||||
|
"ctime": "cpp",
|
||||||
|
"ratio": "cpp",
|
||||||
|
"thread": "cpp",
|
||||||
|
"filesystem": "cpp",
|
||||||
|
"codecvt": "cpp",
|
||||||
|
"iomanip": "cpp"
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,12 @@
|
||||||
|
AM_CXXFLAGS = -std=c++17
|
||||||
|
AUTOMAKE_OPTIONS = subdir-objects
|
||||||
|
bin_PROGRAMS = boxscript
|
||||||
|
|
||||||
|
boxscript_SOURCES = \
|
||||||
|
source/pcapp.cpp \
|
||||||
|
source/parser.cpp \
|
||||||
|
source/dirent.cpp \
|
||||||
|
source/expressions.cpp \
|
||||||
|
source/lexer.cpp \
|
||||||
|
source/networkstream.cpp \
|
||||||
|
source/runtimefuncs.cpp
|
|
@ -0,0 +1,127 @@
|
||||||
|
/* config.h. Generated from config.h.in by configure. */
|
||||||
|
/* config.h.in. Generated from configure.ac by autoheader. */
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <arpa/inet.h> header file. */
|
||||||
|
#define HAVE_ARPA_INET_H 1
|
||||||
|
|
||||||
|
/* Define to 1 if fseeko (and presumably ftello) exists and is declared. */
|
||||||
|
#define HAVE_FSEEKO 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the `gethostbyname' function. */
|
||||||
|
#define HAVE_GETHOSTBYNAME 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the `inet_ntoa' function. */
|
||||||
|
#define HAVE_INET_NTOA 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <inttypes.h> header file. */
|
||||||
|
#define HAVE_INTTYPES_H 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the `curl' library (-lcurl). */
|
||||||
|
#define HAVE_LIBCURL 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the `pthread' library (-lpthread). */
|
||||||
|
#define HAVE_LIBPTHREAD 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <memory.h> header file. */
|
||||||
|
#define HAVE_MEMORY_H 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the `mkdir' function. */
|
||||||
|
#define HAVE_MKDIR 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <netdb.h> header file. */
|
||||||
|
#define HAVE_NETDB_H 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the `socket' function. */
|
||||||
|
#define HAVE_SOCKET 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <stdint.h> header file. */
|
||||||
|
#define HAVE_STDINT_H 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <stdlib.h> header file. */
|
||||||
|
#define HAVE_STDLIB_H 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <strings.h> header file. */
|
||||||
|
#define HAVE_STRINGS_H 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <string.h> header file. */
|
||||||
|
#define HAVE_STRING_H 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <sys/socket.h> header file. */
|
||||||
|
#define HAVE_SYS_SOCKET_H 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <sys/stat.h> header file. */
|
||||||
|
#define HAVE_SYS_STAT_H 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <sys/types.h> header file. */
|
||||||
|
#define HAVE_SYS_TYPES_H 1
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <unistd.h> header file. */
|
||||||
|
#define HAVE_UNISTD_H 1
|
||||||
|
|
||||||
|
/* Define to 1 if the system has the type `_Bool'. */
|
||||||
|
#define HAVE__BOOL 1
|
||||||
|
|
||||||
|
/* Name of package */
|
||||||
|
#define PACKAGE "boxscript"
|
||||||
|
|
||||||
|
/* Define to the address where bug reports for this package should be sent. */
|
||||||
|
#define PACKAGE_BUGREPORT ""
|
||||||
|
|
||||||
|
/* Define to the full name of this package. */
|
||||||
|
#define PACKAGE_NAME "boxscript"
|
||||||
|
|
||||||
|
/* Define to the full name and version of this package. */
|
||||||
|
#define PACKAGE_STRING "boxscript VERSION"
|
||||||
|
|
||||||
|
/* Define to the one symbol short name of this package. */
|
||||||
|
#define PACKAGE_TARNAME "boxscript"
|
||||||
|
|
||||||
|
/* Define to the home page for this package. */
|
||||||
|
#define PACKAGE_URL ""
|
||||||
|
|
||||||
|
/* Define to the version of this package. */
|
||||||
|
#define PACKAGE_VERSION "VERSION"
|
||||||
|
|
||||||
|
/* Define to 1 if you have the ANSI C header files. */
|
||||||
|
#define STDC_HEADERS 1
|
||||||
|
|
||||||
|
/* Version number of package */
|
||||||
|
#define VERSION "VERSION"
|
||||||
|
|
||||||
|
/* Define to 1 to make fseeko visible on some hosts (e.g. glibc 2.2). */
|
||||||
|
/* #undef _LARGEFILE_SOURCE */
|
||||||
|
|
||||||
|
/* Define for Solaris 2.5.1 so the uint32_t typedef from <sys/synch.h>,
|
||||||
|
<pthread.h>, or <semaphore.h> is not used. If the typedef were allowed, the
|
||||||
|
#define below would cause a syntax error. */
|
||||||
|
/* #undef _UINT32_T */
|
||||||
|
|
||||||
|
/* Define for Solaris 2.5.1 so the uint8_t typedef from <sys/synch.h>,
|
||||||
|
<pthread.h>, or <semaphore.h> is not used. If the typedef were allowed, the
|
||||||
|
#define below would cause a syntax error. */
|
||||||
|
/* #undef _UINT8_T */
|
||||||
|
|
||||||
|
/* Define to the type of a signed integer type of width exactly 64 bits if
|
||||||
|
such a type exists and the standard includes do not define it. */
|
||||||
|
/* #undef int64_t */
|
||||||
|
|
||||||
|
/* Define to `long int' if <sys/types.h> does not define. */
|
||||||
|
/* #undef off_t */
|
||||||
|
|
||||||
|
/* Define to `unsigned int' if <sys/types.h> does not define. */
|
||||||
|
/* #undef size_t */
|
||||||
|
|
||||||
|
/* Define to `int' if <sys/types.h> does not define. */
|
||||||
|
/* #undef ssize_t */
|
||||||
|
|
||||||
|
/* Define to the type of an unsigned integer type of width exactly 16 bits if
|
||||||
|
such a type exists and the standard includes do not define it. */
|
||||||
|
/* #undef uint16_t */
|
||||||
|
|
||||||
|
/* Define to the type of an unsigned integer type of width exactly 32 bits if
|
||||||
|
such a type exists and the standard includes do not define it. */
|
||||||
|
/* #undef uint32_t */
|
||||||
|
|
||||||
|
/* Define to the type of an unsigned integer type of width exactly 8 bits if
|
||||||
|
such a type exists and the standard includes do not define it. */
|
||||||
|
/* #undef uint8_t */
|
|
@ -0,0 +1,123 @@
|
||||||
|
/* config.h.in. Generated from configure.ac by autoheader. */
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <arpa/inet.h> header file. */
|
||||||
|
#undef HAVE_ARPA_INET_H
|
||||||
|
|
||||||
|
/* Define to 1 if fseeko (and presumably ftello) exists and is declared. */
|
||||||
|
#undef HAVE_FSEEKO
|
||||||
|
|
||||||
|
/* Define to 1 if you have the `gethostbyname' function. */
|
||||||
|
#undef HAVE_GETHOSTBYNAME
|
||||||
|
|
||||||
|
/* Define to 1 if you have the `inet_ntoa' function. */
|
||||||
|
#undef HAVE_INET_NTOA
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <inttypes.h> header file. */
|
||||||
|
#undef HAVE_INTTYPES_H
|
||||||
|
|
||||||
|
/* Define to 1 if you have the `pthread' library (-lpthread). */
|
||||||
|
#undef HAVE_LIBPTHREAD
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <memory.h> header file. */
|
||||||
|
#undef HAVE_MEMORY_H
|
||||||
|
|
||||||
|
/* Define to 1 if you have the `mkdir' function. */
|
||||||
|
#undef HAVE_MKDIR
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <netdb.h> header file. */
|
||||||
|
#undef HAVE_NETDB_H
|
||||||
|
|
||||||
|
/* Define to 1 if you have the `socket' function. */
|
||||||
|
#undef HAVE_SOCKET
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <stdint.h> header file. */
|
||||||
|
#undef HAVE_STDINT_H
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <stdlib.h> header file. */
|
||||||
|
#undef HAVE_STDLIB_H
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <strings.h> header file. */
|
||||||
|
#undef HAVE_STRINGS_H
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <string.h> header file. */
|
||||||
|
#undef HAVE_STRING_H
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <sys/socket.h> header file. */
|
||||||
|
#undef HAVE_SYS_SOCKET_H
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <sys/stat.h> header file. */
|
||||||
|
#undef HAVE_SYS_STAT_H
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <sys/types.h> header file. */
|
||||||
|
#undef HAVE_SYS_TYPES_H
|
||||||
|
|
||||||
|
/* Define to 1 if you have the <unistd.h> header file. */
|
||||||
|
#undef HAVE_UNISTD_H
|
||||||
|
|
||||||
|
/* Define to 1 if the system has the type `_Bool'. */
|
||||||
|
#undef HAVE__BOOL
|
||||||
|
|
||||||
|
/* Name of package */
|
||||||
|
#undef PACKAGE
|
||||||
|
|
||||||
|
/* Define to the address where bug reports for this package should be sent. */
|
||||||
|
#undef PACKAGE_BUGREPORT
|
||||||
|
|
||||||
|
/* Define to the full name of this package. */
|
||||||
|
#undef PACKAGE_NAME
|
||||||
|
|
||||||
|
/* Define to the full name and version of this package. */
|
||||||
|
#undef PACKAGE_STRING
|
||||||
|
|
||||||
|
/* Define to the one symbol short name of this package. */
|
||||||
|
#undef PACKAGE_TARNAME
|
||||||
|
|
||||||
|
/* Define to the home page for this package. */
|
||||||
|
#undef PACKAGE_URL
|
||||||
|
|
||||||
|
/* Define to the version of this package. */
|
||||||
|
#undef PACKAGE_VERSION
|
||||||
|
|
||||||
|
/* Define to 1 if you have the ANSI C header files. */
|
||||||
|
#undef STDC_HEADERS
|
||||||
|
|
||||||
|
/* Version number of package */
|
||||||
|
#undef VERSION
|
||||||
|
|
||||||
|
/* Define to 1 to make fseeko visible on some hosts (e.g. glibc 2.2). */
|
||||||
|
#undef _LARGEFILE_SOURCE
|
||||||
|
|
||||||
|
/* Define for Solaris 2.5.1 so the uint32_t typedef from <sys/synch.h>,
|
||||||
|
<pthread.h>, or <semaphore.h> is not used. If the typedef were allowed, the
|
||||||
|
#define below would cause a syntax error. */
|
||||||
|
#undef _UINT32_T
|
||||||
|
|
||||||
|
/* Define for Solaris 2.5.1 so the uint8_t typedef from <sys/synch.h>,
|
||||||
|
<pthread.h>, or <semaphore.h> is not used. If the typedef were allowed, the
|
||||||
|
#define below would cause a syntax error. */
|
||||||
|
#undef _UINT8_T
|
||||||
|
|
||||||
|
/* Define to the type of a signed integer type of width exactly 64 bits if
|
||||||
|
such a type exists and the standard includes do not define it. */
|
||||||
|
#undef int64_t
|
||||||
|
|
||||||
|
/* Define to `long int' if <sys/types.h> does not define. */
|
||||||
|
#undef off_t
|
||||||
|
|
||||||
|
/* Define to `unsigned int' if <sys/types.h> does not define. */
|
||||||
|
#undef size_t
|
||||||
|
|
||||||
|
/* Define to `int' if <sys/types.h> does not define. */
|
||||||
|
#undef ssize_t
|
||||||
|
|
||||||
|
/* Define to the type of an unsigned integer type of width exactly 16 bits if
|
||||||
|
such a type exists and the standard includes do not define it. */
|
||||||
|
#undef uint16_t
|
||||||
|
|
||||||
|
/* Define to the type of an unsigned integer type of width exactly 32 bits if
|
||||||
|
such a type exists and the standard includes do not define it. */
|
||||||
|
#undef uint32_t
|
||||||
|
|
||||||
|
/* Define to the type of an unsigned integer type of width exactly 8 bits if
|
||||||
|
such a type exists and the standard includes do not define it. */
|
||||||
|
#undef uint8_t
|
|
@ -0,0 +1,36 @@
|
||||||
|
# -*- Autoconf -*-
|
||||||
|
# Process this file with autoconf to produce a configure script.
|
||||||
|
|
||||||
|
AC_PREREQ([2.69])
|
||||||
|
AC_INIT([boxscript], [VERSION], [])
|
||||||
|
AC_CONFIG_SRCDIR([source/dirent.cpp])
|
||||||
|
AC_CONFIG_HEADERS([config.h])
|
||||||
|
AM_INIT_AUTOMAKE([-Wall -Werror foreign])
|
||||||
|
# Checks for programs.
|
||||||
|
AC_PROG_CXX
|
||||||
|
AC_PROG_CC
|
||||||
|
|
||||||
|
#AC_CHECK_LIB([m], [main])
|
||||||
|
AC_CHECK_LIB([pthread],[pthread_create])
|
||||||
|
AC_CHECK_LIB([curl],[curl_easy_init])
|
||||||
|
|
||||||
|
# Checks for header files.
|
||||||
|
AC_CHECK_HEADERS([arpa/inet.h netdb.h sys/socket.h unistd.h])
|
||||||
|
|
||||||
|
# Checks for typedefs, structures, and compiler characteristics.
|
||||||
|
AC_CHECK_HEADER_STDBOOL
|
||||||
|
AC_TYPE_INT64_T
|
||||||
|
AC_TYPE_OFF_T
|
||||||
|
AC_TYPE_SIZE_T
|
||||||
|
AC_TYPE_SSIZE_T
|
||||||
|
AC_TYPE_UINT16_T
|
||||||
|
AC_TYPE_UINT32_T
|
||||||
|
AC_TYPE_UINT8_T
|
||||||
|
|
||||||
|
# Checks for library functions.
|
||||||
|
AC_FUNC_FSEEKO
|
||||||
|
AC_CHECK_FUNCS([gethostbyname inet_ntoa mkdir socket])
|
||||||
|
|
||||||
|
AC_CONFIG_FILES([Makefile])
|
||||||
|
|
||||||
|
AC_OUTPUT
|
|
@ -0,0 +1,56 @@
|
||||||
|
#include "parser.hpp"
|
||||||
|
#include <dirent.h>
|
||||||
|
#include <sys/stat.h>
|
||||||
|
#include <iostream>
|
||||||
|
#include <filesystem>
|
||||||
|
namespace fs = std::filesystem;
|
||||||
|
|
||||||
|
|
||||||
|
std::vector<std::pair<std::string,bool>> get_entries(std::string path)
|
||||||
|
{
|
||||||
|
std::vector<std::pair<std::string,bool>> entries;
|
||||||
|
#if defined(GEKKO)
|
||||||
|
DIR* dir = opendir(path.c_str());
|
||||||
|
if(dir == NULL)
|
||||||
|
{
|
||||||
|
return entries;
|
||||||
|
}
|
||||||
|
struct dirent* entry;
|
||||||
|
entry = readdir(dir);
|
||||||
|
while(entry != NULL)
|
||||||
|
{
|
||||||
|
entries.push_back({entry->d_name,entry->d_type == DT_DIR});
|
||||||
|
entry = readdir(dir);
|
||||||
|
}
|
||||||
|
closedir(dir);
|
||||||
|
#else
|
||||||
|
for (const auto & entry : fs::directory_iterator(path))
|
||||||
|
entries.push_back({entry.path().filename().c_str(),entry.is_directory()});
|
||||||
|
#endif
|
||||||
|
return entries;
|
||||||
|
|
||||||
|
}
|
||||||
|
std::vector<std::string> get_files(std::string path)
|
||||||
|
{
|
||||||
|
std::vector<std::string> files;
|
||||||
|
for(auto f : get_entries(path))
|
||||||
|
{
|
||||||
|
if(f.first!="." && f.first != ".." && !f.second )
|
||||||
|
{
|
||||||
|
files.push_back(f.first);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return files;
|
||||||
|
}
|
||||||
|
std::vector<std::string> get_directories(std::string path)
|
||||||
|
{
|
||||||
|
std::vector<std::string> files;
|
||||||
|
for(auto f : get_entries(path))
|
||||||
|
{
|
||||||
|
if(f.first!="." && f.first != ".." && f.second )
|
||||||
|
{
|
||||||
|
files.push_back(f.first);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return files;
|
||||||
|
}
|
|
@ -0,0 +1,258 @@
|
||||||
|
#include "parser.hpp"
|
||||||
|
namespace BoxScript
|
||||||
|
{
|
||||||
|
#pragma region "ConstantNumber"
|
||||||
|
ConstantNumber::ConstantNumber(string num)
|
||||||
|
{
|
||||||
|
this->num=stoll(num);
|
||||||
|
}
|
||||||
|
int64_t ConstantNumber::Evaluate(IApplicationState* state)
|
||||||
|
{
|
||||||
|
return this->num;
|
||||||
|
}
|
||||||
|
string ConstantNumber::GetNodeName()
|
||||||
|
{
|
||||||
|
return "ConstantNumber";
|
||||||
|
}
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "VariableGetValueNode"
|
||||||
|
string VariableGetValueNode::GetName()
|
||||||
|
{
|
||||||
|
return this->var;
|
||||||
|
}
|
||||||
|
string VariableGetValueNode::GetNodeName()
|
||||||
|
{
|
||||||
|
return "VariableGetValueNode";
|
||||||
|
}
|
||||||
|
VariableGetValueNode::VariableGetValueNode(string var)
|
||||||
|
{
|
||||||
|
this->var = var;
|
||||||
|
}
|
||||||
|
int64_t VariableGetValueNode::Evaluate(IApplicationState* state)
|
||||||
|
{
|
||||||
|
return state->GetVariable(this->var);
|
||||||
|
}
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "StringNode"
|
||||||
|
string StringNode::GetText()
|
||||||
|
{
|
||||||
|
return this->text;
|
||||||
|
}
|
||||||
|
string StringNode::GetNodeName()
|
||||||
|
{
|
||||||
|
return "StringNode";
|
||||||
|
}
|
||||||
|
StringNode::StringNode(string var)
|
||||||
|
{
|
||||||
|
this->boxId=-1;
|
||||||
|
this->text=var;
|
||||||
|
}
|
||||||
|
int64_t StringNode::Evaluate(IApplicationState* state)
|
||||||
|
{
|
||||||
|
if(boxId > -1)
|
||||||
|
return boxId;
|
||||||
|
|
||||||
|
boxId = state->CreateBoxPermanent(text);
|
||||||
|
return boxId;
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "SetVariableNode"
|
||||||
|
SetVariableNode::~SetVariableNode()
|
||||||
|
{
|
||||||
|
delete this->e;
|
||||||
|
}
|
||||||
|
string SetVariableNode::GetNodeName()
|
||||||
|
{
|
||||||
|
return "SetVariableNode";
|
||||||
|
}
|
||||||
|
SetVariableNode::SetVariableNode(Expression* expression,string name)
|
||||||
|
{
|
||||||
|
this->e = expression;
|
||||||
|
this->vname =name;
|
||||||
|
}
|
||||||
|
int64_t SetVariableNode::Evaluate(IApplicationState* state)
|
||||||
|
{
|
||||||
|
int64_t v = e->Evaluate(state);
|
||||||
|
state->SetVariable(vname,v);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "FunctionCallNode"
|
||||||
|
FunctionCallNode::~FunctionCallNode()
|
||||||
|
{
|
||||||
|
for(auto node: this->expressions)
|
||||||
|
{
|
||||||
|
delete node;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
string FunctionCallNode::GetNodeName()
|
||||||
|
{
|
||||||
|
return "FunctionCallNode";
|
||||||
|
}
|
||||||
|
FunctionCallNode::FunctionCallNode(string _name,vector<Expression*> exps)
|
||||||
|
{
|
||||||
|
this->name = _name;
|
||||||
|
this->expressions =exps;
|
||||||
|
}
|
||||||
|
int64_t FunctionCallNode::Evaluate(IApplicationState* state)
|
||||||
|
{
|
||||||
|
if(state->HasRuntimeFunction(name))
|
||||||
|
{
|
||||||
|
return state->GetRuntimeFunction(name)(state,expressions);
|
||||||
|
}
|
||||||
|
if(state->HasFunction(name))
|
||||||
|
{
|
||||||
|
return state->ExecuteFunction(name,expressions);
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "AddNode"
|
||||||
|
AddNode::~AddNode()
|
||||||
|
{
|
||||||
|
delete left;
|
||||||
|
delete right;
|
||||||
|
}
|
||||||
|
string AddNode::GetNodeName()
|
||||||
|
{
|
||||||
|
return "AddNode";
|
||||||
|
}
|
||||||
|
AddNode::AddNode(Expression* _left,Expression* _right)
|
||||||
|
{
|
||||||
|
this->left=_left;
|
||||||
|
this->right = _right;
|
||||||
|
}
|
||||||
|
int64_t AddNode::Evaluate(IApplicationState* state)
|
||||||
|
{
|
||||||
|
return this->left->Evaluate(state) + this->right->Evaluate(state);
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "MinusNode"
|
||||||
|
MinusNode::~MinusNode()
|
||||||
|
{
|
||||||
|
delete left;
|
||||||
|
delete right;
|
||||||
|
}
|
||||||
|
string MinusNode::GetNodeName()
|
||||||
|
{
|
||||||
|
return "MinusNode";
|
||||||
|
}
|
||||||
|
MinusNode::MinusNode(Expression* _left,Expression* _right)
|
||||||
|
{
|
||||||
|
this->left=_left;
|
||||||
|
this->right = _right;
|
||||||
|
}
|
||||||
|
int64_t MinusNode::Evaluate(IApplicationState* state)
|
||||||
|
{
|
||||||
|
return this->left->Evaluate(state) - this->right->Evaluate(state);
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "MultiplyNode"
|
||||||
|
MultiplyNode::~MultiplyNode()
|
||||||
|
{
|
||||||
|
delete left;
|
||||||
|
delete right;
|
||||||
|
}
|
||||||
|
string MultiplyNode::GetNodeName()
|
||||||
|
{
|
||||||
|
return "MultiplyNode";
|
||||||
|
}
|
||||||
|
MultiplyNode::MultiplyNode(Expression* _left,Expression* _right)
|
||||||
|
{
|
||||||
|
this->left=_left;
|
||||||
|
this->right = _right;
|
||||||
|
}
|
||||||
|
int64_t MultiplyNode::Evaluate(IApplicationState* state)
|
||||||
|
{
|
||||||
|
return this->left->Evaluate(state) * this->right->Evaluate(state);
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "DivideNode"
|
||||||
|
DivideNode::~DivideNode()
|
||||||
|
{
|
||||||
|
delete left;
|
||||||
|
delete right;
|
||||||
|
}
|
||||||
|
string DivideNode::GetNodeName()
|
||||||
|
{
|
||||||
|
return "DivideNode";
|
||||||
|
}
|
||||||
|
DivideNode::DivideNode(Expression* _left,Expression* _right)
|
||||||
|
{
|
||||||
|
this->left=_left;
|
||||||
|
this->right = _right;
|
||||||
|
}
|
||||||
|
int64_t DivideNode::Evaluate(IApplicationState* state)
|
||||||
|
{
|
||||||
|
return this->left->Evaluate(state) / this->right->Evaluate(state);
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "ModulusNode"
|
||||||
|
ModulusNode::~ModulusNode()
|
||||||
|
{
|
||||||
|
delete left;
|
||||||
|
delete right;
|
||||||
|
}
|
||||||
|
string ModulusNode::GetNodeName()
|
||||||
|
{
|
||||||
|
return "ModulusNode";
|
||||||
|
}
|
||||||
|
ModulusNode::ModulusNode(Expression* _left,Expression* _right)
|
||||||
|
{
|
||||||
|
this->left=_left;
|
||||||
|
this->right = _right;
|
||||||
|
}
|
||||||
|
int64_t ModulusNode::Evaluate(IApplicationState* state)
|
||||||
|
{
|
||||||
|
return this->left->Evaluate(state) % this->right->Evaluate(state);
|
||||||
|
}
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "ListNode"
|
||||||
|
void ListNode::DisableScope()
|
||||||
|
{
|
||||||
|
this->root=true;
|
||||||
|
}
|
||||||
|
ListNode::~ListNode()
|
||||||
|
{
|
||||||
|
for(auto node : nodes)
|
||||||
|
{
|
||||||
|
delete node;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
string ListNode::GetNodeName()
|
||||||
|
{
|
||||||
|
return "ListNode";
|
||||||
|
}
|
||||||
|
|
||||||
|
int64_t ListNode::Evaluate(IApplicationState* state)
|
||||||
|
{
|
||||||
|
int64_t res=0;
|
||||||
|
IApplicationState* s=state;
|
||||||
|
if(!root)
|
||||||
|
{
|
||||||
|
s=s->NewScope();
|
||||||
|
s->AddThreadOwner();
|
||||||
|
}
|
||||||
|
for(auto node : nodes)
|
||||||
|
{
|
||||||
|
state->ExitIfNotRunning();
|
||||||
|
res= node->Evaluate(state);
|
||||||
|
}
|
||||||
|
if(!root)
|
||||||
|
{
|
||||||
|
s->RemoveThreadOwner();
|
||||||
|
}
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
#pragma endregion
|
||||||
|
void Expression::DisableScope()
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
};
|
|
@ -0,0 +1,293 @@
|
||||||
|
#include "lexer.hpp"
|
||||||
|
namespace BoxScript::Lexer
|
||||||
|
{
|
||||||
|
LexToken::LexToken()
|
||||||
|
{
|
||||||
|
this->text="";
|
||||||
|
this->type = ERROR;
|
||||||
|
}
|
||||||
|
LexToken::LexToken(std::string _text)
|
||||||
|
{
|
||||||
|
this->text = _text;
|
||||||
|
if(_text.size() > 0)
|
||||||
|
{
|
||||||
|
this->type=_text[0] >= '0' && _text[0] <= '9' ? NUMBER : IDENTIFER;
|
||||||
|
}
|
||||||
|
else{
|
||||||
|
this->type = ERROR;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
class Lexer
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
std::string text;
|
||||||
|
int filePos;
|
||||||
|
void read_char(char* chr,bool* esc)
|
||||||
|
{
|
||||||
|
int txt = text[filePos++];
|
||||||
|
if(txt == '\\')
|
||||||
|
{
|
||||||
|
txt = text[filePos++];
|
||||||
|
if(txt == 'x')
|
||||||
|
{
|
||||||
|
std::string txt="0x";
|
||||||
|
filePos+=2;
|
||||||
|
for(int i = 0;i<2;i++)
|
||||||
|
{
|
||||||
|
txt += text[filePos++];
|
||||||
|
}
|
||||||
|
*chr= (char)std::stol(txt,0,0);
|
||||||
|
}else
|
||||||
|
{
|
||||||
|
if(txt == 'n')
|
||||||
|
{
|
||||||
|
*chr= '\n';
|
||||||
|
}else
|
||||||
|
if(txt == 'r')
|
||||||
|
{
|
||||||
|
*chr='\r';
|
||||||
|
}else
|
||||||
|
if(txt == 't')
|
||||||
|
{
|
||||||
|
*chr='\t';
|
||||||
|
}else{
|
||||||
|
*chr = (char)txt;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
*esc=true;
|
||||||
|
}
|
||||||
|
else{
|
||||||
|
*esc=false;
|
||||||
|
*chr=(char)txt;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
std::string read_string()
|
||||||
|
{
|
||||||
|
std::string b="";
|
||||||
|
while(true)
|
||||||
|
{
|
||||||
|
char chr='\0';
|
||||||
|
bool esc=false;
|
||||||
|
read_char(&chr,&esc);
|
||||||
|
if(chr == '\"' && !esc)
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
b+=chr;
|
||||||
|
}
|
||||||
|
return b;
|
||||||
|
}
|
||||||
|
public:
|
||||||
|
Lexer(std::string _text)
|
||||||
|
{
|
||||||
|
this->text=_text;
|
||||||
|
this->filePos=0;
|
||||||
|
}
|
||||||
|
std::vector<LexToken> Lex()
|
||||||
|
{
|
||||||
|
std::vector<LexToken> tokens;
|
||||||
|
std::string b="";
|
||||||
|
while(filePos < text.length())
|
||||||
|
{
|
||||||
|
char c = text[filePos++];
|
||||||
|
if(c == '\"')
|
||||||
|
{
|
||||||
|
if(b.length() > 0)
|
||||||
|
{
|
||||||
|
tokens.push_back(LexToken(b));
|
||||||
|
b="";
|
||||||
|
}
|
||||||
|
std::string str = read_string();
|
||||||
|
LexToken token;
|
||||||
|
token.text = str;
|
||||||
|
token.type = STRING;
|
||||||
|
tokens.push_back(token);
|
||||||
|
}else if(c == '#')
|
||||||
|
{
|
||||||
|
while(text[filePos++] != '\n');
|
||||||
|
}
|
||||||
|
else
|
||||||
|
if(c == '\'')
|
||||||
|
{
|
||||||
|
if(b.length() > 0)
|
||||||
|
{
|
||||||
|
tokens.push_back(LexToken(b));
|
||||||
|
b="";
|
||||||
|
}
|
||||||
|
char chr='\0';
|
||||||
|
bool esc;
|
||||||
|
read_char(&chr,&esc);
|
||||||
|
LexToken token;
|
||||||
|
token.text="";
|
||||||
|
token.text += chr;
|
||||||
|
token.type = NUMBER;
|
||||||
|
tokens.push_back(token);
|
||||||
|
|
||||||
|
}else if(c == '+')
|
||||||
|
{
|
||||||
|
if(b.length() > 0)
|
||||||
|
{
|
||||||
|
tokens.push_back(LexToken(b));
|
||||||
|
b="";
|
||||||
|
}
|
||||||
|
LexToken token;
|
||||||
|
token.text="+";
|
||||||
|
token.type = PLUS;
|
||||||
|
tokens.push_back(token);
|
||||||
|
}else if(c == '-')
|
||||||
|
{
|
||||||
|
if(b.length() > 0)
|
||||||
|
{
|
||||||
|
tokens.push_back(LexToken(b));
|
||||||
|
b="";
|
||||||
|
}
|
||||||
|
LexToken token;
|
||||||
|
token.text="-";
|
||||||
|
token.type = MINUS;
|
||||||
|
tokens.push_back(token);
|
||||||
|
}else if(c == '+')
|
||||||
|
{
|
||||||
|
if(b.length() > 0)
|
||||||
|
{
|
||||||
|
tokens.push_back(LexToken(b));
|
||||||
|
b="";
|
||||||
|
}
|
||||||
|
LexToken token;
|
||||||
|
token.text="*";
|
||||||
|
token.type = MULTIPLY;
|
||||||
|
tokens.push_back(token);
|
||||||
|
}
|
||||||
|
else if(c == '/')
|
||||||
|
{
|
||||||
|
if(b.length() > 0)
|
||||||
|
{
|
||||||
|
tokens.push_back(LexToken(b));
|
||||||
|
b="";
|
||||||
|
}
|
||||||
|
LexToken token;
|
||||||
|
token.text="/";
|
||||||
|
token.type = DIVIDE;
|
||||||
|
tokens.push_back(token);
|
||||||
|
}else if(c == '%')
|
||||||
|
{
|
||||||
|
if(b.length() > 0)
|
||||||
|
{
|
||||||
|
tokens.push_back(LexToken(b));
|
||||||
|
b="";
|
||||||
|
}
|
||||||
|
LexToken token;
|
||||||
|
token.text="%";
|
||||||
|
token.type = MOD;
|
||||||
|
tokens.push_back(token);
|
||||||
|
}
|
||||||
|
else if(c == '{')
|
||||||
|
{
|
||||||
|
if(b.length() > 0)
|
||||||
|
{
|
||||||
|
tokens.push_back(LexToken(b));
|
||||||
|
b="";
|
||||||
|
}
|
||||||
|
LexToken token;
|
||||||
|
token.text="{";
|
||||||
|
token.type = LBRACE;
|
||||||
|
tokens.push_back(token);
|
||||||
|
}
|
||||||
|
else if(c == '}')
|
||||||
|
{
|
||||||
|
if(b.length() > 0)
|
||||||
|
{
|
||||||
|
tokens.push_back(LexToken(b));
|
||||||
|
b="";
|
||||||
|
}
|
||||||
|
LexToken token;
|
||||||
|
token.text="}";
|
||||||
|
token.type = RBRACE;
|
||||||
|
tokens.push_back(token);
|
||||||
|
}
|
||||||
|
else if(c == '(')
|
||||||
|
{
|
||||||
|
if(b.length() > 0)
|
||||||
|
{
|
||||||
|
tokens.push_back(LexToken(b));
|
||||||
|
b="";
|
||||||
|
}
|
||||||
|
LexToken token;
|
||||||
|
token.text="(";
|
||||||
|
token.type = LPAREN;
|
||||||
|
tokens.push_back(token);
|
||||||
|
}
|
||||||
|
else if(c == ')')
|
||||||
|
{
|
||||||
|
if(b.length() > 0)
|
||||||
|
{
|
||||||
|
tokens.push_back(LexToken(b));
|
||||||
|
b="";
|
||||||
|
}
|
||||||
|
LexToken token;
|
||||||
|
token.text=")";
|
||||||
|
token.type = RPAREN;
|
||||||
|
tokens.push_back(token);
|
||||||
|
}
|
||||||
|
else if(c == '=')
|
||||||
|
{
|
||||||
|
if(b.length() > 0)
|
||||||
|
{
|
||||||
|
tokens.push_back(LexToken(b));
|
||||||
|
b="";
|
||||||
|
}
|
||||||
|
LexToken token;
|
||||||
|
token.text="=";
|
||||||
|
token.type = EQUALS;
|
||||||
|
tokens.push_back(token);
|
||||||
|
}
|
||||||
|
else if(c == ',')
|
||||||
|
{
|
||||||
|
if(b.length() > 0)
|
||||||
|
{
|
||||||
|
tokens.push_back(LexToken(b));
|
||||||
|
b="";
|
||||||
|
}
|
||||||
|
LexToken token;
|
||||||
|
token.text=",";
|
||||||
|
token.type = COMMA;
|
||||||
|
tokens.push_back(token);
|
||||||
|
}
|
||||||
|
else if(c == ';')
|
||||||
|
{
|
||||||
|
if(b.length() > 0)
|
||||||
|
{
|
||||||
|
tokens.push_back(LexToken(b));
|
||||||
|
b="";
|
||||||
|
}
|
||||||
|
LexToken token;
|
||||||
|
token.text=";";
|
||||||
|
token.type = SEMI;
|
||||||
|
tokens.push_back(token);
|
||||||
|
}
|
||||||
|
else if(c == '\n' || c == ' ' || c == '\t')
|
||||||
|
{
|
||||||
|
if(b.length() > 0)
|
||||||
|
{
|
||||||
|
tokens.push_back(LexToken(b));
|
||||||
|
b="";
|
||||||
|
}
|
||||||
|
|
||||||
|
}else{
|
||||||
|
b += c;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(b.length() > 0)
|
||||||
|
{
|
||||||
|
tokens.push_back(LexToken(b));
|
||||||
|
b="";
|
||||||
|
}
|
||||||
|
return tokens;
|
||||||
|
}
|
||||||
|
|
||||||
|
};
|
||||||
|
std::vector<LexToken> Lex(std::string text)
|
||||||
|
{
|
||||||
|
Lexer l(text);
|
||||||
|
return l.Lex();
|
||||||
|
}
|
||||||
|
};
|
|
@ -0,0 +1,34 @@
|
||||||
|
#pragma once
|
||||||
|
#include <string>
|
||||||
|
#include <vector>
|
||||||
|
namespace BoxScript::Lexer
|
||||||
|
{
|
||||||
|
enum LexTokenType
|
||||||
|
{
|
||||||
|
PLUS,
|
||||||
|
MINUS,
|
||||||
|
MULTIPLY,
|
||||||
|
DIVIDE,
|
||||||
|
MOD,
|
||||||
|
LPAREN,
|
||||||
|
RPAREN,
|
||||||
|
IDENTIFER,
|
||||||
|
NUMBER,
|
||||||
|
EQUALS,
|
||||||
|
COMMA,
|
||||||
|
ERROR,
|
||||||
|
SEMI,
|
||||||
|
LBRACE,
|
||||||
|
RBRACE,
|
||||||
|
STRING
|
||||||
|
};
|
||||||
|
class LexToken
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
std::string text;
|
||||||
|
LexTokenType type;
|
||||||
|
LexToken();
|
||||||
|
LexToken(std::string _text);
|
||||||
|
};
|
||||||
|
std::vector<LexToken> Lex(std::string text);
|
||||||
|
};
|
|
@ -0,0 +1,352 @@
|
||||||
|
|
||||||
|
#include "parser.hpp"
|
||||||
|
#include <cstring>
|
||||||
|
#if defined(GEKKO)
|
||||||
|
int net_initialized = 0;
|
||||||
|
char bba_local_ip[16];
|
||||||
|
char bba_netmask[16];
|
||||||
|
char bba_gateway[16];
|
||||||
|
#if defined(HW_DOL)
|
||||||
|
#include <ogc/exi.h>
|
||||||
|
|
||||||
|
int bba_exists = 0;
|
||||||
|
unsigned int exi_get_id(int chn, int dev)
|
||||||
|
{
|
||||||
|
u32 cid = 0;
|
||||||
|
EXI_GetID(chn,dev,&cid);
|
||||||
|
return cid;
|
||||||
|
}
|
||||||
|
|
||||||
|
int exi_bba_exists()
|
||||||
|
{
|
||||||
|
return exi_get_id(EXI_CHANNEL_0,EXI_DEVICE_2) == EXI_BBA_ID;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
namespace BoxScript
|
||||||
|
{
|
||||||
|
void sockets_free()
|
||||||
|
{
|
||||||
|
#if defined(HW_RVL) && defined(LIBWIISOCKET)
|
||||||
|
wiisocket_deinit();
|
||||||
|
#elif defined(HW_RVL) && !defined(LIBWIISOCKET)
|
||||||
|
net_deinit();
|
||||||
|
#elif defined(_WIN32) || defined(WIN32)
|
||||||
|
WSACleanup();
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
int NetworkInit()
|
||||||
|
{
|
||||||
|
#if defined(LIBWIISOCKET)
|
||||||
|
return wiisocket_init();
|
||||||
|
#endif
|
||||||
|
#if defined(GEKKO) && !defined(LIBWIISOCKET)
|
||||||
|
int res;
|
||||||
|
#if defined(HW_DOL)
|
||||||
|
|
||||||
|
bba_exists = exi_bba_exists();
|
||||||
|
if(bba_exists && !net_initialized) {
|
||||||
|
#else
|
||||||
|
if(!net_initialized){
|
||||||
|
#endif
|
||||||
|
res = if_config(bba_local_ip, bba_netmask, bba_gateway, true,20);
|
||||||
|
if(res >= 0 && strcmp("255.255.255.255", bba_local_ip)) {
|
||||||
|
net_initialized = 1;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
net_initialized = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#elif defined(_WIN32) || defined(WIN32)
|
||||||
|
int err= WSAStartup(0x202, &wsaData);
|
||||||
|
if (err != 0) {
|
||||||
|
/* Tell the user that we could not find a usable */
|
||||||
|
/* Winsock DLL. */
|
||||||
|
printf("WSAStartup failed with error: %d\n", err);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Confirm that the WinSock DLL supports 2.2.*/
|
||||||
|
/* Note that if the DLL supports versions greater */
|
||||||
|
/* than 2.2 in addition to 2.2, it will still return */
|
||||||
|
/* 2.2 in wVersion since that is the version we */
|
||||||
|
/* requested. */
|
||||||
|
|
||||||
|
if (LOBYTE(wsaData.wVersion) != 2 || HIBYTE(wsaData.wVersion) != 2) {
|
||||||
|
/* Tell the user that we could not find a usable */
|
||||||
|
/* WinSock DLL. */
|
||||||
|
printf("Could not find a usable version of Winsock.dll\n");
|
||||||
|
WSACleanup();
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
#else
|
||||||
|
|
||||||
|
#endif
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
NetworkStream::NetworkStream(SOCKET i)
|
||||||
|
{
|
||||||
|
this->fd = i;
|
||||||
|
}
|
||||||
|
|
||||||
|
void NetworkStream::Write(uint8_t* data,size_t len)
|
||||||
|
{
|
||||||
|
#if defined(OGC_NETWORKING)
|
||||||
|
net_send(this->fd,data,len,0);
|
||||||
|
#else
|
||||||
|
int flags=0;
|
||||||
|
#if __linux__
|
||||||
|
flags=MSG_NOSIGNAL;
|
||||||
|
#endif
|
||||||
|
send(this->fd,data,len,flags);
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
size_t NetworkStream::Read(uint8_t* data,size_t len)
|
||||||
|
{
|
||||||
|
#if defined(OGC_NETWORKING)
|
||||||
|
ssize_t v=(ssize_t)net_recv(this->fd,data,len,0);
|
||||||
|
if(v < 0) return 0;
|
||||||
|
return (size_t)v;
|
||||||
|
#else
|
||||||
|
int flags=0;
|
||||||
|
#if __linux__
|
||||||
|
flags=MSG_NOSIGNAL;
|
||||||
|
#endif
|
||||||
|
ssize_t v=recv(this->fd,data,len,flags);
|
||||||
|
if(v < 0) return 0;
|
||||||
|
return (size_t)v;
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
int64_t NetworkStream::GetPosition()
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
int64_t NetworkStream::GetLength()
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
void NetworkStream::SetPosition(int64_t pos)
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
void NetworkStream::Flush()
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
void NetworkStream::Close()
|
||||||
|
{
|
||||||
|
#if defined(OGC_NETWORKING)
|
||||||
|
net_close(this->fd);
|
||||||
|
#else
|
||||||
|
close(this->fd);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
}
|
||||||
|
bool NetworkStream::CanRead()
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
bool NetworkStream::CanWrite()
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
bool NetworkStream::CanSeek()
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
struct hostent* _______ghbn(string ip)
|
||||||
|
{
|
||||||
|
#if defined(GEKKO) && !defined(LIBWIISOCKET)
|
||||||
|
return net_gethostbyname(ip.c_str());
|
||||||
|
#else
|
||||||
|
return gethostbyname(ip.c_str());
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
NetworkStream* NetClient(string ip,int64_t port,SOCKET fd)
|
||||||
|
|
||||||
|
{
|
||||||
|
struct sockaddr_in serv_addr;
|
||||||
|
serv_addr.sin_family = AF_INET;
|
||||||
|
serv_addr.sin_port = htons((uint16_t)port);
|
||||||
|
|
||||||
|
if (inet_aton( ip.c_str(), &serv_addr.sin_addr)
|
||||||
|
<= 0) {
|
||||||
|
struct hostent* host=_______ghbn(ip);
|
||||||
|
struct in_addr **addr_list;
|
||||||
|
|
||||||
|
addr_list = (struct in_addr **)host->h_addr_list;
|
||||||
|
if(host->h_length > 0)
|
||||||
|
{
|
||||||
|
memcpy(&serv_addr.sin_addr,addr_list[0],sizeof(struct in_addr));
|
||||||
|
}else{
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#if defined(GEKKO) && !defined(LIBWIISOCKET)
|
||||||
|
if(net_connect(fd,(struct sockaddr*)&serv_addr,sizeof(struct sockaddr_in)))
|
||||||
|
{
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
if(connect(fd,(struct sockaddr*)&serv_addr,sizeof(struct sockaddr_in)))
|
||||||
|
{
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
return new NetworkStream(fd);
|
||||||
|
}
|
||||||
|
SOCKET NetServerInit(string ip,int64_t port,int fd)
|
||||||
|
{
|
||||||
|
struct sockaddr_in serv_addr;
|
||||||
|
serv_addr.sin_family = AF_INET;
|
||||||
|
serv_addr.sin_port = htons(port);
|
||||||
|
|
||||||
|
if (inet_aton( ip.c_str(), &serv_addr.sin_addr)
|
||||||
|
<= 0) {
|
||||||
|
struct hostent* host=_______ghbn(ip);
|
||||||
|
struct in_addr **addr_list;
|
||||||
|
|
||||||
|
addr_list = (struct in_addr **)host->h_addr_list;
|
||||||
|
if(host->h_length > 0)
|
||||||
|
{
|
||||||
|
memcpy(&serv_addr.sin_addr,addr_list[0],sizeof(struct in_addr));
|
||||||
|
}else{
|
||||||
|
throw exception();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#if defined(GEKKO) && !defined(LIBWIISOCKET)
|
||||||
|
if(net_bind(fd,(struct sockaddr*)&serv_addr,sizeof(struct sockaddr_in))< 0)
|
||||||
|
{
|
||||||
|
printf("bind error, is your computer already listening on that port\n");
|
||||||
|
throw exception();
|
||||||
|
}
|
||||||
|
if(net_listen(fd,100) > 0)
|
||||||
|
{
|
||||||
|
printf("listen error");
|
||||||
|
throw exception();
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
if(bind(fd,(struct sockaddr*)&serv_addr,sizeof(struct sockaddr_in))< 0)
|
||||||
|
{
|
||||||
|
printf("bind error, is your computer already listening on that port\n");
|
||||||
|
throw exception();
|
||||||
|
}
|
||||||
|
if(listen(fd,100) > 0)
|
||||||
|
{
|
||||||
|
printf("listen error");
|
||||||
|
throw exception();
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
return fd;
|
||||||
|
}
|
||||||
|
|
||||||
|
SOCKET TcpServerInit(string ip,int64_t port)
|
||||||
|
{
|
||||||
|
SOCKET fd;
|
||||||
|
|
||||||
|
#if defined(GEKKO) && !defined(LIBWIISOCKET)
|
||||||
|
if ((fd = net_socket(AF_INET, SOCK_STREAM, 0)) < 0) {
|
||||||
|
printf("\n Socket creation error \n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
if ((fd = socket(AF_INET, SOCK_STREAM, 0)) < 0) {
|
||||||
|
printf("\n Socket creation error \n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
return NetServerInit(ip,port,fd);
|
||||||
|
}
|
||||||
|
SOCKET UdpServerInit(string ip,int64_t port)
|
||||||
|
{
|
||||||
|
SOCKET fd;
|
||||||
|
|
||||||
|
#if defined(GEKKO) && !defined(LIBWIISOCKET)
|
||||||
|
if ((fd = net_socket(AF_INET, SOCK_DGRAM, 0)) < 0) {
|
||||||
|
printf("\n Socket creation error \n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
if ((fd = socket(AF_INET, SOCK_DGRAM, 0)) < 0) {
|
||||||
|
printf("\n Socket creation error \n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
return NetServerInit(ip,port,fd);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
Stream* AcceptClient(SOCKET fd,string* ip)
|
||||||
|
{
|
||||||
|
struct sockaddr_in clt_addr;
|
||||||
|
socklen_t clt_addr_len = sizeof(struct sockaddr_in);
|
||||||
|
#if defined(GEKKO) && !defined(LIBWIISOCKET)
|
||||||
|
int cltFd=net_accept(fd,(struct sockaddr*)&clt_addr,&clt_addr_len);
|
||||||
|
#else
|
||||||
|
#if defined(_WIN32) || defined(WIN32)
|
||||||
|
SOCKET cltFd=accept(fd,(struct sockaddr*)&clt_addr,&clt_addr_len);
|
||||||
|
#else
|
||||||
|
int cltFd=accept(fd,(struct sockaddr*)&clt_addr,&clt_addr_len);
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
ip->append(inet_ntoa(clt_addr.sin_addr));
|
||||||
|
|
||||||
|
return new NetworkStream(cltFd);
|
||||||
|
}
|
||||||
|
NetworkStream* TcpClient(string ip,int64_t port)
|
||||||
|
{
|
||||||
|
|
||||||
|
#if defined(_WIN32) || defined(WIN32)
|
||||||
|
SOCKET fd;
|
||||||
|
#else
|
||||||
|
int fd;
|
||||||
|
#endif
|
||||||
|
#if defined(GEKKO) && !defined(LIBWIISOCKET)
|
||||||
|
if ((fd = net_socket(AF_INET, SOCK_STREAM, 0)) < 0) {
|
||||||
|
printf("\n Socket creation error \n");
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
if ((fd = socket(AF_INET, SOCK_STREAM, 0)) < 0) {
|
||||||
|
printf("\n Socket creation error \n");
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
return NetClient(ip,port,fd);
|
||||||
|
}
|
||||||
|
|
||||||
|
NetworkStream* UdpClient(string ip,int64_t port)
|
||||||
|
{
|
||||||
|
#if defined(_WIN32) || defined(WIN32)
|
||||||
|
SOCKET fd;
|
||||||
|
#else
|
||||||
|
int fd;
|
||||||
|
#endif
|
||||||
|
#if defined(GEKKO) && !defined(LIBWIISOCKET)
|
||||||
|
if ((fd = net_socket(AF_INET, SOCK_DGRAM, 0)) < 0) {
|
||||||
|
printf("\n Socket creation error \n");
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
if ((fd = socket(AF_INET, SOCK_DGRAM, 0)) < 0) {
|
||||||
|
printf("\n Socket creation error \n");
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
return NetClient(ip,port,fd);
|
||||||
|
}
|
||||||
|
|
||||||
|
};
|
|
@ -0,0 +1,984 @@
|
||||||
|
#include "parser.hpp"
|
||||||
|
#include <algorithm>
|
||||||
|
#include <cstring>
|
||||||
|
namespace BoxScript
|
||||||
|
{
|
||||||
|
void IApplicationState::AddThreadOwner()
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
void IApplicationState::RemoveThreadOwner()
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::AddThreadOwner()
|
||||||
|
{
|
||||||
|
this->state->AddThreadOwner();
|
||||||
|
this->threads++;
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::RemoveThreadOwner()
|
||||||
|
{
|
||||||
|
this->state->RemoveThreadOwner();
|
||||||
|
if(this->threads <= 0)
|
||||||
|
{
|
||||||
|
delete this;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
ApplicationState::ApplicationState()
|
||||||
|
{
|
||||||
|
this->isRunning=true;
|
||||||
|
this->NoBoxes=0;
|
||||||
|
this->NoExpressions=0;
|
||||||
|
this->NoStreams=0;
|
||||||
|
}
|
||||||
|
int64_t ApplicationState::CreateBox(string text)
|
||||||
|
{
|
||||||
|
int64_t boxId=this->NoBoxes++;
|
||||||
|
if(this->boxes.count(boxId) <= 0)
|
||||||
|
{
|
||||||
|
this->boxes.insert({boxId,{vector<int64_t>(), false}});
|
||||||
|
}
|
||||||
|
for(int i =0;i<text.length();i++)
|
||||||
|
{
|
||||||
|
this->boxes[boxId].first.push_back(text[i]);
|
||||||
|
}
|
||||||
|
|
||||||
|
return boxId;
|
||||||
|
}
|
||||||
|
|
||||||
|
Expression* ApplicationState::Calln(int64_t e)
|
||||||
|
{
|
||||||
|
if(this->expressions.count(e) > 0)
|
||||||
|
{
|
||||||
|
return expressions[e];
|
||||||
|
}
|
||||||
|
return new ConstantNumber("0");
|
||||||
|
}
|
||||||
|
int64_t ApplicationState::ReadByteFromStream(int64_t streamId)
|
||||||
|
{
|
||||||
|
Stream* strm = GetStream(streamId);
|
||||||
|
return strm->ReadByte();
|
||||||
|
}
|
||||||
|
int64_t ApplicationState::CreateBufferedStream(int64_t existingStreamId)
|
||||||
|
{
|
||||||
|
Stream* strm = GetStream(existingStreamId);
|
||||||
|
return CreateStream(new BufferedStream(strm));
|
||||||
|
}
|
||||||
|
int64_t ApplicationState::e2n(Expression* e)
|
||||||
|
{
|
||||||
|
int64_t eId = this->NoExpressions++;
|
||||||
|
this->expressions.insert({eId,e});
|
||||||
|
return eId;
|
||||||
|
}
|
||||||
|
string ApplicationState::BoxToString(int64_t boxId)
|
||||||
|
{
|
||||||
|
string s ="";
|
||||||
|
if(boxes.count(boxId) == 0)
|
||||||
|
{
|
||||||
|
throw exception();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
for(int i =0;i<boxes[boxId].first.size();i++)
|
||||||
|
{
|
||||||
|
char c = (char)(boxes[boxId].first[i] % 256);
|
||||||
|
s+= c;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return s;
|
||||||
|
}
|
||||||
|
int64_t ApplicationState::CreateBox(int boxLen)
|
||||||
|
{
|
||||||
|
int64_t i = NoBoxes++;
|
||||||
|
if(this->boxes.count(i) <= 0)
|
||||||
|
{
|
||||||
|
this->boxes.insert({i,{vector<int64_t>(), false}});
|
||||||
|
}
|
||||||
|
this->boxes[i].first.reserve(boxLen);
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
void ApplicationState::AddRuntimeFunction(string str,internal_func func)
|
||||||
|
{
|
||||||
|
if(!HasRuntimeFunction(str))
|
||||||
|
{
|
||||||
|
runtime_funcs.insert({str,func});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void ApplicationState::DestroyBox(int64_t boxId)
|
||||||
|
{
|
||||||
|
if(boxes.count(boxId) == 0) return;
|
||||||
|
if(!boxes[boxId].second)
|
||||||
|
{
|
||||||
|
boxes[boxId].first.clear();
|
||||||
|
boxes.erase(boxId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
int64_t ApplicationState::CreateStream(Stream* strm)
|
||||||
|
{
|
||||||
|
int64_t i = NoStreams++;
|
||||||
|
streams.insert({i,strm});
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
int64_t ApplicationState::GetBoxValue(int64_t bId,int index)
|
||||||
|
{
|
||||||
|
if(boxes.count(bId) == 0)
|
||||||
|
{
|
||||||
|
throw exception();
|
||||||
|
}else
|
||||||
|
{
|
||||||
|
if(index>boxes[bId].first.size())
|
||||||
|
{
|
||||||
|
throw exception();
|
||||||
|
}else{
|
||||||
|
return boxes[bId].first[index];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
void ApplicationState::SetBoxValue(int64_t bId,int index,int64_t value)
|
||||||
|
{
|
||||||
|
if(value > 2147483647) throw exception();
|
||||||
|
|
||||||
|
if(boxes.count(bId) == 0)
|
||||||
|
{
|
||||||
|
throw exception();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if(boxes[bId].second) throw new exception();
|
||||||
|
if(index > boxes[bId].first.size())
|
||||||
|
{
|
||||||
|
throw exception();
|
||||||
|
}else{
|
||||||
|
boxes[bId].first[index] = value;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
bool ApplicationState::HasVariable(string name)
|
||||||
|
{
|
||||||
|
return variables.count(name) > 0;
|
||||||
|
}
|
||||||
|
int64_t ApplicationState::GetVariable(string name)
|
||||||
|
{
|
||||||
|
if(variables.count(name) > 0)
|
||||||
|
{
|
||||||
|
return variables[name];
|
||||||
|
}else{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
IApplicationState* ApplicationState::NewScope()
|
||||||
|
{
|
||||||
|
return new SubscopeApplicationState(this);
|
||||||
|
}
|
||||||
|
void ApplicationState::SetVariable(string name,int64_t value)
|
||||||
|
{
|
||||||
|
if(variables.count(name) > 0)
|
||||||
|
{
|
||||||
|
variables[name]=value;
|
||||||
|
}else{
|
||||||
|
variables.insert({name,value});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
void ApplicationState::ClearBox(int64_t bId)
|
||||||
|
{
|
||||||
|
if(boxes.count(bId) == 0)
|
||||||
|
{
|
||||||
|
throw exception();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if(boxes[bId].second) throw exception();
|
||||||
|
boxes[bId].first.clear();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
void ApplicationState::AddToBox(int64_t bId,int64_t value)
|
||||||
|
{
|
||||||
|
if(boxes.count(bId) == 0)
|
||||||
|
{
|
||||||
|
throw exception();
|
||||||
|
}else
|
||||||
|
{
|
||||||
|
if(boxes[bId].second) throw exception();
|
||||||
|
boxes[bId].first.push_back(value);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
void ApplicationState::RemoveFromBox(int64_t bId,int64_t value)
|
||||||
|
{
|
||||||
|
if(boxes.count(bId)==0)
|
||||||
|
{
|
||||||
|
throw exception();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if(boxes[bId].second) throw exception();
|
||||||
|
vector<int64_t>::iterator itr= find(boxes[bId].first.begin(),boxes[bId].first.end(),value);
|
||||||
|
if(itr < boxes[bId].first.end())
|
||||||
|
{
|
||||||
|
boxes[bId].first.erase(itr);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
void ApplicationState::RemoveAtFromBox(int64_t bId,int index)
|
||||||
|
{
|
||||||
|
if(boxes.count(bId)==0)
|
||||||
|
{
|
||||||
|
throw exception();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if(boxes[bId].second) throw exception();
|
||||||
|
vector<int64_t>::iterator itr= boxes[bId].first.begin() + index;
|
||||||
|
if(itr < boxes[bId].first.end())
|
||||||
|
{
|
||||||
|
boxes[bId].first.erase(itr);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
void ApplicationState::InsertToBox(int64_t bId,int index,int64_t value)
|
||||||
|
{
|
||||||
|
if(boxes.count(bId)==0)
|
||||||
|
{
|
||||||
|
throw exception();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if(boxes[bId].second) throw exception();
|
||||||
|
vector<int64_t>::iterator itr= boxes[bId].first.begin() + index;
|
||||||
|
if(itr != boxes[bId].first.end())
|
||||||
|
{
|
||||||
|
boxes[bId].first.insert(itr,value);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
int64_t ApplicationState::BoxLength(int64_t boxId)
|
||||||
|
{
|
||||||
|
if(boxes.count(boxId)==0)
|
||||||
|
{
|
||||||
|
throw exception();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return boxes[boxId].first.size();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
bool ApplicationState::HasRuntimeFunction(string str)
|
||||||
|
{
|
||||||
|
return runtime_funcs.count(str) > 0;
|
||||||
|
}
|
||||||
|
internal_func ApplicationState::GetRuntimeFunction(string str)
|
||||||
|
{
|
||||||
|
return runtime_funcs[str];
|
||||||
|
}
|
||||||
|
int64_t ApplicationState::ExecuteFunction(string str,vector<Expression*> expressions)
|
||||||
|
{
|
||||||
|
if(!HasFunction(str)) return 0;
|
||||||
|
//var func=methods[str]
|
||||||
|
IApplicationState* res = NewScope();
|
||||||
|
res->AddThreadOwner();
|
||||||
|
for(int i = 0;i<min(expressions.size(),methods[str].first.size());i++)
|
||||||
|
{
|
||||||
|
res->SetVariable(methods[str].first[i],expressions[i]->Evaluate(res));
|
||||||
|
}
|
||||||
|
int64_t result= methods[str].second->Evaluate(res);
|
||||||
|
res->RemoveThreadOwner();
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
int64_t ApplicationState::CreateBoxPermanent(string text)
|
||||||
|
{
|
||||||
|
int64_t boxId=this->NoBoxes++;
|
||||||
|
if(this->boxes.count(boxId) <= 0)
|
||||||
|
{
|
||||||
|
this->boxes.insert({boxId,{vector<int64_t>(), true}});
|
||||||
|
}
|
||||||
|
for(int i =0;i<text.length();i++)
|
||||||
|
{
|
||||||
|
this->boxes[boxId].first.push_back(text[i]);
|
||||||
|
}
|
||||||
|
|
||||||
|
return boxId;
|
||||||
|
}
|
||||||
|
bool ApplicationState::HasFunction(string str)
|
||||||
|
{
|
||||||
|
return methods.count(str) > 0;
|
||||||
|
}
|
||||||
|
void ApplicationState::AddFunction(string str,vector<string> args,Expression* exp)
|
||||||
|
{
|
||||||
|
if(!HasFunction(str))
|
||||||
|
{
|
||||||
|
methods.insert({str,{args,exp}});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
void ApplicationState::CopyStream(int64_t src,int64_t dest)
|
||||||
|
{
|
||||||
|
if(streams.count(src) == 0 || streams.count(dest) == 0) return;
|
||||||
|
GetStream(src)->CopyTo(GetStream(dest));
|
||||||
|
}
|
||||||
|
Stream* ApplicationState::GetStream(int64_t streamId)
|
||||||
|
{
|
||||||
|
if(streams.count(streamId) == 0) throw exception();
|
||||||
|
return streams[streamId];
|
||||||
|
}
|
||||||
|
void ApplicationState::CloseStream(int64_t streamId)
|
||||||
|
{
|
||||||
|
|
||||||
|
if(streams.count(streamId)==0) throw exception();
|
||||||
|
streams[streamId]->Close();
|
||||||
|
delete streams[streamId];
|
||||||
|
streams.erase(streamId);
|
||||||
|
|
||||||
|
}
|
||||||
|
void ApplicationState::WriteToStream(int64_t streamId,int64_t boxId,int64_t offset,int64_t len)
|
||||||
|
{
|
||||||
|
if(streams.count(streamId) == 0) return;
|
||||||
|
Stream* strm=GetStream(streamId);
|
||||||
|
if(!strm->CanWrite())return;
|
||||||
|
size_t len2=boxes[boxId].first.size();
|
||||||
|
len2-=offset;
|
||||||
|
int64_t len3=min(len,(int64_t)len2);
|
||||||
|
uint8_t data[len3];
|
||||||
|
for(int64_t i = 0;i<len3;i++)
|
||||||
|
{
|
||||||
|
uint8_t byte=(uint8_t)boxes[boxId].first[i+offset];
|
||||||
|
data[i] = byte;
|
||||||
|
}
|
||||||
|
strm->Write(data,(size_t)len3);
|
||||||
|
}
|
||||||
|
int64_t ApplicationState::ReadFromStream(int64_t streamId,int64_t boxId,int64_t offset,int64_t len)
|
||||||
|
{
|
||||||
|
if(streams.count(streamId) == 0) return 0;
|
||||||
|
Stream* strm=GetStream(streamId);
|
||||||
|
if(boxes[boxId].second || !strm->CanRead()) return 0;
|
||||||
|
size_t len2=boxes[boxId].first.size();
|
||||||
|
len2-=offset;
|
||||||
|
int64_t len3=min(len,(int64_t)len2);
|
||||||
|
uint8_t data[len3];
|
||||||
|
len3=strm->Read(data,len3);
|
||||||
|
for(int64_t i = 0;i<len3;i++)
|
||||||
|
{
|
||||||
|
boxes[boxId].first[i+offset]=data[i];
|
||||||
|
}
|
||||||
|
return len3;
|
||||||
|
}
|
||||||
|
void ApplicationState::SetStreamPosition(int64_t streamId,int64_t streamPos)
|
||||||
|
{
|
||||||
|
if(streams.count(streamId) == 0) return;
|
||||||
|
Stream* strm=GetStream(streamId);
|
||||||
|
if(!strm->CanSeek()) return;
|
||||||
|
strm->SetPosition(streamPos);
|
||||||
|
}
|
||||||
|
int64_t ApplicationState::GetStreamLength(int64_t streamId)
|
||||||
|
{
|
||||||
|
if(streams.count(streamId) == 0) return 0;
|
||||||
|
Stream* strm=GetStream(streamId);
|
||||||
|
return strm->GetLength();
|
||||||
|
}
|
||||||
|
int64_t ApplicationState::GetStreamPosition(int64_t streamId)
|
||||||
|
{
|
||||||
|
if(streams.count(streamId) == 0) return 0;
|
||||||
|
Stream* strm=GetStream(streamId);
|
||||||
|
if(!strm->CanSeek()) return 0;
|
||||||
|
return strm->GetPosition();
|
||||||
|
}
|
||||||
|
bool ApplicationState::CanRead(int64_t streamId)
|
||||||
|
{
|
||||||
|
if(streams.count(streamId) == 0) return false;
|
||||||
|
return GetStream(streamId)->CanRead();
|
||||||
|
}
|
||||||
|
bool ApplicationState::CanWrite(int64_t streamId)
|
||||||
|
{
|
||||||
|
if(streams.count(streamId) == 0) return false;
|
||||||
|
return GetStream(streamId)->CanWrite();
|
||||||
|
}
|
||||||
|
bool ApplicationState::CanSeek(int64_t streamId)
|
||||||
|
{
|
||||||
|
if(streams.count(streamId) == 0) return false;
|
||||||
|
return GetStream(streamId)->CanSeek();
|
||||||
|
}
|
||||||
|
void ApplicationState::FlushStream(int64_t streamId)
|
||||||
|
{
|
||||||
|
if(streams.count(streamId) == 0) return;
|
||||||
|
GetStream(streamId)->Flush();
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma region SubscopeApplicationState
|
||||||
|
SubscopeApplicationState::SubscopeApplicationState(IApplicationState* _state)
|
||||||
|
{
|
||||||
|
this->threads=0;
|
||||||
|
this->state=_state;
|
||||||
|
}
|
||||||
|
internal_func SubscopeApplicationState::GetRuntimeFunction(string str)
|
||||||
|
{
|
||||||
|
return this->state->GetRuntimeFunction(str);
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::FlushStream(int64_t stream)
|
||||||
|
{
|
||||||
|
this->state->FlushStream(stream);
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::DestroyBox(int64_t id)
|
||||||
|
{
|
||||||
|
this->state->DestroyBox(id);
|
||||||
|
}
|
||||||
|
int64_t SubscopeApplicationState::e2n(Expression* e)
|
||||||
|
{
|
||||||
|
return this->state->e2n(e);
|
||||||
|
}
|
||||||
|
Expression* SubscopeApplicationState::Calln(int64_t e)
|
||||||
|
{
|
||||||
|
return this->state->Calln(e);
|
||||||
|
}
|
||||||
|
int64_t SubscopeApplicationState::CreateStream(Stream* strm)
|
||||||
|
{
|
||||||
|
return this->state->CreateStream(strm);
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::CopyStream(int64_t strmSrc,int64_t strmDest)
|
||||||
|
{
|
||||||
|
this->state->CopyStream(strmSrc,strmDest);
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::CloseStream(int64_t streamId)
|
||||||
|
{
|
||||||
|
this->state->CloseStream(streamId);
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::WriteToStream(int64_t streamId,int64_t boxId,int64_t offset,int64_t len)
|
||||||
|
{
|
||||||
|
this->state->WriteToStream(streamId,boxId,offset,len);
|
||||||
|
}
|
||||||
|
int64_t SubscopeApplicationState::ReadFromStream(int64_t streamId,int64_t boxId,int64_t offset,int64_t len)
|
||||||
|
{
|
||||||
|
return this->state->ReadFromStream(streamId,boxId,offset,len);
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::SetStreamPosition(int64_t streamId,int64_t streamPos)
|
||||||
|
{
|
||||||
|
this->state->SetStreamPosition(streamId,streamPos);
|
||||||
|
}
|
||||||
|
int64_t SubscopeApplicationState::GetStreamPosition(int64_t streamId)
|
||||||
|
{
|
||||||
|
return this->state->GetStreamPosition(streamId);
|
||||||
|
}
|
||||||
|
int64_t SubscopeApplicationState::GetStreamLength(int64_t streamId)
|
||||||
|
{
|
||||||
|
return this->state->GetStreamLength(streamId);
|
||||||
|
}
|
||||||
|
bool SubscopeApplicationState::CanRead(int64_t streamId)
|
||||||
|
{
|
||||||
|
return this->state->CanRead(streamId);
|
||||||
|
}
|
||||||
|
bool SubscopeApplicationState::CanWrite(int64_t streamId)
|
||||||
|
{
|
||||||
|
return this->state->CanWrite(streamId);
|
||||||
|
}
|
||||||
|
bool SubscopeApplicationState::CanSeek(int64_t streamId)
|
||||||
|
{
|
||||||
|
return this->state->CanSeek(streamId);
|
||||||
|
}
|
||||||
|
int64_t SubscopeApplicationState::ExecuteFunction(string str,vector<Expression*> expressions)
|
||||||
|
{
|
||||||
|
return this->state->ExecuteFunction(str,expressions);
|
||||||
|
}
|
||||||
|
bool SubscopeApplicationState::HasRuntimeFunction(string str)
|
||||||
|
{
|
||||||
|
return this->state->HasRuntimeFunction(str);
|
||||||
|
}
|
||||||
|
bool SubscopeApplicationState::HasFunction(string str)
|
||||||
|
{
|
||||||
|
return this->state->HasFunction(str);
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::AddFunction(string str,vector<string> args,Expression* exp)
|
||||||
|
{
|
||||||
|
this->state->AddFunction(str,args,exp);
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::AddRuntimeFunction(string str,internal_func func)
|
||||||
|
{
|
||||||
|
this->state->AddRuntimeFunction(str,func);
|
||||||
|
}
|
||||||
|
string SubscopeApplicationState::BoxToString(int64_t boxId)
|
||||||
|
{
|
||||||
|
return this->state->BoxToString(boxId);
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::ClearBox(int64_t bId)
|
||||||
|
{
|
||||||
|
this->state->ClearBox(bId);
|
||||||
|
}
|
||||||
|
int64_t SubscopeApplicationState::ReadByteFromStream(int64_t streamId)
|
||||||
|
{
|
||||||
|
return this->state->ReadByteFromStream(streamId);
|
||||||
|
}
|
||||||
|
int64_t SubscopeApplicationState::CreateBufferedStream(int64_t existingStreamId)
|
||||||
|
{
|
||||||
|
return this->state->CreateBufferedStream(existingStreamId);
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::AddToBox(int64_t bId,int64_t value)
|
||||||
|
{
|
||||||
|
this->state->AddToBox(bId,value);
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::RemoveFromBox(int64_t bId,int64_t value)
|
||||||
|
{
|
||||||
|
this->state->RemoveFromBox(bId,value);
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::RemoveAtFromBox(int64_t bId,int index)
|
||||||
|
{
|
||||||
|
this->state->RemoveAtFromBox(bId,index);
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::InsertToBox(int64_t bId,int index,int64_t value)
|
||||||
|
{
|
||||||
|
this->state->InsertToBox(bId,index,value);
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::SetBoxValue(int64_t bId,int index,int64_t value)
|
||||||
|
{
|
||||||
|
this->state->SetBoxValue(bId,index,value);
|
||||||
|
}
|
||||||
|
int64_t SubscopeApplicationState::BoxLength(int64_t boxId)
|
||||||
|
{
|
||||||
|
return this->state->BoxLength(boxId);
|
||||||
|
}
|
||||||
|
int64_t SubscopeApplicationState::CreateBox(int len)
|
||||||
|
{
|
||||||
|
return this->state->CreateBox(len);
|
||||||
|
}
|
||||||
|
int64_t SubscopeApplicationState::CreateBox(string text)
|
||||||
|
{
|
||||||
|
return this->state->CreateBox(text);
|
||||||
|
}
|
||||||
|
int64_t SubscopeApplicationState::CreateBoxPermanent(string text)
|
||||||
|
{
|
||||||
|
return this->state->CreateBoxPermanent(text);
|
||||||
|
}
|
||||||
|
int64_t SubscopeApplicationState::GetBoxValue(int64_t bId, int index)
|
||||||
|
{
|
||||||
|
return this->state->GetBoxValue(bId,index);
|
||||||
|
}
|
||||||
|
bool SubscopeApplicationState::HasVariable(string name)
|
||||||
|
{
|
||||||
|
return variables.count(name) > 0 || (name.substr(0,4) != "cur." && this->state->HasVariable(name));
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::SetVariable(string name,int64_t value)
|
||||||
|
{
|
||||||
|
if(name.substr(0,4) != "cur." && state->HasVariable(name))
|
||||||
|
{
|
||||||
|
this->state->SetVariable(name,value);
|
||||||
|
}else{
|
||||||
|
if(this->variables.count(name) > 0)
|
||||||
|
{
|
||||||
|
variables[name]=value;
|
||||||
|
}else{
|
||||||
|
variables.insert({name,value});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
int64_t SubscopeApplicationState::GetVariable(string name)
|
||||||
|
{
|
||||||
|
if(name.substr(0,4) != "cur." && state->HasVariable(name))
|
||||||
|
{
|
||||||
|
return this->state->GetVariable(name);
|
||||||
|
}else{
|
||||||
|
if(this->variables.count(name) > 0) return this->variables[name];
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
IApplicationState* SubscopeApplicationState::NewScope()
|
||||||
|
{
|
||||||
|
return new SubscopeApplicationState(this);
|
||||||
|
}
|
||||||
|
#pragma endregion
|
||||||
|
|
||||||
|
|
||||||
|
void Stream::CopyTo(Stream* strm)
|
||||||
|
{
|
||||||
|
uint8_t buffer[4096];
|
||||||
|
size_t read;
|
||||||
|
do
|
||||||
|
{
|
||||||
|
read = this->Read(buffer,4096);
|
||||||
|
strm->Write(buffer,read);
|
||||||
|
} while (read != 0);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
ExpressionStream::ExpressionStream(IApplicationState* state,vector<Expression*> expressions)
|
||||||
|
{
|
||||||
|
this->st = state;
|
||||||
|
this->exp = exp;
|
||||||
|
|
||||||
|
}
|
||||||
|
void ExpressionStream::Write(uint8_t* data,size_t len)
|
||||||
|
{
|
||||||
|
int64_t box = st->CreateBox((int64_t)len);
|
||||||
|
IApplicationState* newSc = st->NewScope();
|
||||||
|
newSc->AddThreadOwner();
|
||||||
|
newSc->SetVariable("stream_count_value",len);
|
||||||
|
newSc->SetVariable("stream_buffer",box);
|
||||||
|
|
||||||
|
for(size_t i = 0;i<len;i++)
|
||||||
|
{
|
||||||
|
st->AddToBox(box,data[i]);
|
||||||
|
}
|
||||||
|
exp[1]->Evaluate(newSc);
|
||||||
|
newSc->DestroyBox(box);
|
||||||
|
newSc->RemoveThreadOwner();
|
||||||
|
}
|
||||||
|
size_t ExpressionStream::Read(uint8_t* data,size_t len)
|
||||||
|
{
|
||||||
|
int64_t box = st->CreateBox((int64_t)len);
|
||||||
|
IApplicationState* newSc = st->NewScope();
|
||||||
|
newSc->AddThreadOwner();
|
||||||
|
newSc->SetVariable("stream_count_value",len);
|
||||||
|
newSc->SetVariable("stream_buffer",box);
|
||||||
|
size_t read = (size_t)exp[0]->Evaluate(newSc);
|
||||||
|
for(size_t i = 0;i<min(read,len);i++)
|
||||||
|
{
|
||||||
|
uint8_t v = (uint8_t)st->GetBoxValue(box,(int)i);
|
||||||
|
data[i]=v;
|
||||||
|
}
|
||||||
|
newSc->DestroyBox(box);
|
||||||
|
newSc->RemoveThreadOwner();
|
||||||
|
return min(read,len);
|
||||||
|
}
|
||||||
|
int64_t ExpressionStream::GetPosition()
|
||||||
|
{
|
||||||
|
//3
|
||||||
|
return exp[3]->Evaluate(st);
|
||||||
|
}
|
||||||
|
int64_t ExpressionStream::GetLength()
|
||||||
|
{
|
||||||
|
//4
|
||||||
|
return exp[4]->Evaluate(st) > 0;
|
||||||
|
}
|
||||||
|
void ExpressionStream::SetPosition(int64_t pos)
|
||||||
|
{
|
||||||
|
//2
|
||||||
|
IApplicationState* newSc = st->NewScope();
|
||||||
|
newSc->AddThreadOwner();
|
||||||
|
newSc->SetVariable("stream_length_value",pos);
|
||||||
|
exp[2]->Evaluate(newSc);
|
||||||
|
newSc->RemoveThreadOwner();
|
||||||
|
}
|
||||||
|
void ExpressionStream::Flush()
|
||||||
|
{
|
||||||
|
//8
|
||||||
|
exp[8]->Evaluate(st);
|
||||||
|
}
|
||||||
|
void ExpressionStream::Close()
|
||||||
|
{
|
||||||
|
//9
|
||||||
|
exp[9]->Evaluate(st);
|
||||||
|
}
|
||||||
|
bool ExpressionStream::CanRead()
|
||||||
|
{
|
||||||
|
//5
|
||||||
|
return exp[5]->Evaluate(st) > 0;
|
||||||
|
}
|
||||||
|
bool ExpressionStream::CanWrite()
|
||||||
|
{
|
||||||
|
//6
|
||||||
|
return exp[6]->Evaluate(st) > 0;
|
||||||
|
}
|
||||||
|
bool ExpressionStream::CanSeek()
|
||||||
|
{
|
||||||
|
//7
|
||||||
|
return exp[7]->Evaluate(st) > 0;
|
||||||
|
}
|
||||||
|
FileStream::FileStream(FILE* fs,bool canRead,bool canWrite,bool canSeek,bool ownFile)
|
||||||
|
{
|
||||||
|
this->f=fs;
|
||||||
|
this->cr = canRead;
|
||||||
|
this->cw = canWrite;
|
||||||
|
this->cs = canSeek;
|
||||||
|
this->own=ownFile;
|
||||||
|
}
|
||||||
|
bool FileStream::CanSeek()
|
||||||
|
{
|
||||||
|
return this->cs;
|
||||||
|
}
|
||||||
|
bool FileStream::CanRead()
|
||||||
|
{
|
||||||
|
return this->cr;
|
||||||
|
}
|
||||||
|
bool FileStream::CanWrite()
|
||||||
|
{
|
||||||
|
return this->cw;
|
||||||
|
}
|
||||||
|
void FileStream::Write(uint8_t* data,size_t len)
|
||||||
|
{
|
||||||
|
if(!cw) return;
|
||||||
|
fwrite(data,1,len,f);
|
||||||
|
}
|
||||||
|
size_t FileStream::Read(uint8_t* data,size_t len)
|
||||||
|
{
|
||||||
|
if(!cr) return 0;
|
||||||
|
return fread(data,1,len,f);
|
||||||
|
}
|
||||||
|
void FileStream::Flush()
|
||||||
|
{
|
||||||
|
fflush(f);
|
||||||
|
}
|
||||||
|
void FileStream::Close()
|
||||||
|
{
|
||||||
|
if(own)
|
||||||
|
fclose(f);
|
||||||
|
}
|
||||||
|
int64_t FileStream::GetPosition()
|
||||||
|
{
|
||||||
|
if(!cs) return 0;
|
||||||
|
return (int64_t)ftello(f);
|
||||||
|
}
|
||||||
|
int64_t FileStream::GetLength()
|
||||||
|
{
|
||||||
|
if(!cs) return 0;
|
||||||
|
fpos_t pos;
|
||||||
|
|
||||||
|
|
||||||
|
fgetpos(f,&pos);
|
||||||
|
fseeko(f,0,SEEK_END);
|
||||||
|
int64_t len= (int64_t)ftello(f);
|
||||||
|
fsetpos(f,&pos);
|
||||||
|
return len;
|
||||||
|
}
|
||||||
|
void FileStream::SetPosition(int64_t pos)
|
||||||
|
{
|
||||||
|
if(!cs) return;
|
||||||
|
fseeko(f,(off_t)pos,SEEK_SET);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Parse(ListNode* node,vector<Lexer::LexToken> tokens)
|
||||||
|
{
|
||||||
|
int i = 0;
|
||||||
|
ParseNode(node,tokens,&i,true);
|
||||||
|
}
|
||||||
|
ListNode* Parse(vector<Lexer::LexToken> tokens)
|
||||||
|
{
|
||||||
|
ListNode* node = new ListNode();
|
||||||
|
Parse(node,tokens);
|
||||||
|
return node;
|
||||||
|
}
|
||||||
|
void ParseNode(ListNode* node,vector<Lexer::LexToken> tokens,int* i)
|
||||||
|
{
|
||||||
|
ParseNode(node,tokens,i,false);
|
||||||
|
}
|
||||||
|
void ParseNode(ListNode* node,vector<Lexer::LexToken> tokens,int* i,bool root)
|
||||||
|
{
|
||||||
|
node->root = root;
|
||||||
|
while(*i < tokens.size() && tokens[*i].type != Lexer::RBRACE)
|
||||||
|
{
|
||||||
|
if(tokens[*i].type == Lexer::SEMI) (*i)++;
|
||||||
|
if(*i+2 < tokens.size() && tokens[*i+1].type == Lexer::EQUALS )
|
||||||
|
{
|
||||||
|
string varname = tokens[*i].text;
|
||||||
|
*i=*i+2;
|
||||||
|
node->nodes.push_back(new SetVariableNode(ParseExpression(tokens,i),varname));
|
||||||
|
if(!root && *i<tokens.size() && tokens[*i].type == Lexer::RBRACE) break;
|
||||||
|
(*i)++;
|
||||||
|
}
|
||||||
|
else if(*i+1 < tokens.size() && tokens[*i+1].type == Lexer::LPAREN)
|
||||||
|
{
|
||||||
|
node->nodes.push_back(ParseExpression(tokens,i));
|
||||||
|
if(!root && *i<tokens.size() && tokens[*i].type == Lexer::RBRACE) break;
|
||||||
|
(*i)++;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
node->nodes.push_back(ParseExpression(tokens,i));
|
||||||
|
if(!root && *i<tokens.size() && tokens[*i].type == Lexer::RBRACE) break;
|
||||||
|
(*i)++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Expression* ParseExpression(vector<Lexer::LexToken> tokens,int* i)
|
||||||
|
{
|
||||||
|
Expression* res = ParseTerm(tokens,i);
|
||||||
|
while(*i < tokens.size() && (tokens[*i].type == Lexer::PLUS||tokens[*i].type == Lexer::MINUS))
|
||||||
|
{
|
||||||
|
if(*i < tokens.size() && tokens[*i].type == Lexer::PLUS)
|
||||||
|
{
|
||||||
|
(*i)++;
|
||||||
|
res = (Expression*)new AddNode(res,ParseTerm(tokens,i));
|
||||||
|
}
|
||||||
|
if(*i < tokens.size() && tokens[*i].type == Lexer::MINUS)
|
||||||
|
{
|
||||||
|
(*i)++;
|
||||||
|
res = (Expression*)new MinusNode(res,ParseTerm(tokens,i));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
Expression* ParseTerm(vector<Lexer::LexToken> tokens,int* i)
|
||||||
|
{
|
||||||
|
Expression* res = ParseFactor(tokens,i);
|
||||||
|
while(*i < tokens.size() && (tokens[*i].type == Lexer::MULTIPLY||tokens[*i].type == Lexer::DIVIDE ||tokens[*i].type == Lexer::MOD))
|
||||||
|
{
|
||||||
|
if(*i < tokens.size() && tokens[*i].type == Lexer::MULTIPLY)
|
||||||
|
{
|
||||||
|
(*i)++;
|
||||||
|
res = (Expression*)new MultiplyNode(res,ParseFactor(tokens,i));
|
||||||
|
}
|
||||||
|
if(*i < tokens.size() && tokens[*i].type == Lexer::DIVIDE)
|
||||||
|
{
|
||||||
|
(*i)++;
|
||||||
|
res = (Expression*)new DivideNode(res,ParseFactor(tokens,i));
|
||||||
|
}
|
||||||
|
if(*i < tokens.size() && tokens[*i].type == Lexer::MOD)
|
||||||
|
{
|
||||||
|
(*i)++;
|
||||||
|
res = (Expression*)new ModulusNode(res,ParseFactor(tokens,i));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
Expression* ParseFactor(vector<Lexer::LexToken> tokens,int* i)
|
||||||
|
{
|
||||||
|
if(*i>=tokens.size()) throw exception();
|
||||||
|
Lexer::LexToken token = tokens[*i];
|
||||||
|
if(token.type == Lexer::LPAREN)
|
||||||
|
{
|
||||||
|
(*i)++;
|
||||||
|
Expression* res = ParseExpression(tokens,i);
|
||||||
|
if(*i>=tokens.size()) throw exception();
|
||||||
|
if(tokens[*i].type != Lexer::RPAREN) throw exception();
|
||||||
|
(*i)++;
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
if(token.type == Lexer::LBRACE)
|
||||||
|
{
|
||||||
|
(*i)++;
|
||||||
|
ListNode* res = new ListNode();
|
||||||
|
ParseNode(res,tokens,i,false);
|
||||||
|
if(*i>=tokens.size()) throw exception();
|
||||||
|
if(tokens[*i].type != Lexer::RBRACE) throw exception();
|
||||||
|
(*i)++;
|
||||||
|
return (Expression*)res;
|
||||||
|
}
|
||||||
|
if(token.type == Lexer::IDENTIFER)
|
||||||
|
{
|
||||||
|
(*i)++;
|
||||||
|
if(*i<tokens.size() && tokens[*i].type == Lexer::LPAREN)
|
||||||
|
{
|
||||||
|
vector<Expression*> funcArgs;
|
||||||
|
(*i)++;
|
||||||
|
while(*i<tokens.size() && tokens[*i].type != Lexer::RPAREN)
|
||||||
|
{
|
||||||
|
if(tokens[*i].type == Lexer::COMMA) (*i)++;
|
||||||
|
funcArgs.push_back(ParseExpression(tokens,i));
|
||||||
|
}
|
||||||
|
(*i)++;
|
||||||
|
return (Expression*)new FunctionCallNode(token.text,funcArgs);
|
||||||
|
}else{
|
||||||
|
return (Expression*)new VariableGetValueNode(token.text);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(token.type == Lexer::STRING)
|
||||||
|
{
|
||||||
|
(*i)++;
|
||||||
|
return (Expression*)new StringNode(token.text);
|
||||||
|
}
|
||||||
|
if(token.type == Lexer::NUMBER)
|
||||||
|
{
|
||||||
|
(*i)++;
|
||||||
|
return (Expression*)new ConstantNumber(token.text);
|
||||||
|
}
|
||||||
|
throw exception();
|
||||||
|
}
|
||||||
|
void ApplicationState::StopRunning()
|
||||||
|
{
|
||||||
|
std::vector<Expression*> exp;
|
||||||
|
this->isRunning=(bool)this->ExecuteFunction("stopinterrupt",exp);
|
||||||
|
}
|
||||||
|
void ApplicationState::ExitIfNotRunning()
|
||||||
|
{
|
||||||
|
if(!isRunning)
|
||||||
|
{
|
||||||
|
exit(0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::StopRunning()
|
||||||
|
{
|
||||||
|
this->state->StopRunning();
|
||||||
|
}
|
||||||
|
void SubscopeApplicationState::ExitIfNotRunning()
|
||||||
|
{
|
||||||
|
this->state->ExitIfNotRunning();
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma region "BufferedStream"
|
||||||
|
BufferedStream::BufferedStream(Stream* parent)
|
||||||
|
{
|
||||||
|
|
||||||
|
this->strm = parent;
|
||||||
|
|
||||||
|
}
|
||||||
|
int64_t Stream::ReadByte()
|
||||||
|
{
|
||||||
|
uint8_t buffer[1];
|
||||||
|
return this->Read(buffer,1) > 0 ? buffer[0] : -1;
|
||||||
|
}
|
||||||
|
int64_t BufferedStream::ReadByte()
|
||||||
|
{
|
||||||
|
if(pos<min((int)this->readIn,4096))
|
||||||
|
{
|
||||||
|
return (int64_t)this->buffer[this->pos];
|
||||||
|
}else{
|
||||||
|
this->readIn=this->strm->Read(this->buffer,4096);
|
||||||
|
this->pos = 0;
|
||||||
|
|
||||||
|
if(this->readIn > 0)
|
||||||
|
{
|
||||||
|
return this->buffer[this->pos++];
|
||||||
|
}else{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
void BufferedStream::Write(uint8_t* data,size_t len)
|
||||||
|
{
|
||||||
|
this->strm->Write(data,len);
|
||||||
|
}
|
||||||
|
size_t BufferedStream::Read(uint8_t* data,size_t len)
|
||||||
|
{
|
||||||
|
if(this->pos<min((int)this->readIn,4096) && this->pos > 0)
|
||||||
|
{
|
||||||
|
int _len=min((int)this->readIn-this->pos,(int)len);
|
||||||
|
memcpy(data,this->buffer + this->pos,_len);
|
||||||
|
this->pos+=_len;
|
||||||
|
return _len;
|
||||||
|
}else{
|
||||||
|
return this->strm->Read(data,len);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
int64_t BufferedStream::GetPosition()
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
int64_t BufferedStream::GetLength()
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
void BufferedStream::SetPosition(int64_t pos)
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
void BufferedStream::Flush()
|
||||||
|
{
|
||||||
|
this->strm->Flush();
|
||||||
|
}
|
||||||
|
void BufferedStream::Close()
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
bool BufferedStream::CanRead()
|
||||||
|
{
|
||||||
|
return this->strm->CanRead();
|
||||||
|
}
|
||||||
|
bool BufferedStream::CanWrite()
|
||||||
|
{
|
||||||
|
return this->strm->CanWrite();
|
||||||
|
}
|
||||||
|
bool BufferedStream::CanSeek()
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
#pragma endregion
|
||||||
|
};
|
|
@ -0,0 +1,537 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#define _FILE_OFFSET_BITS 64
|
||||||
|
#include <string>
|
||||||
|
#include <cstdint>
|
||||||
|
#include <vector>
|
||||||
|
#include <unordered_map>
|
||||||
|
#include <cstdbool>
|
||||||
|
#include <atomic>
|
||||||
|
#include "config.h"
|
||||||
|
#include "lexer.hpp"
|
||||||
|
|
||||||
|
#if defined(GEKKO) && !defined(LIBWIISOCKET)
|
||||||
|
#define OGC_NETWORKING
|
||||||
|
#include <network.h>
|
||||||
|
typedef int SOCKET;
|
||||||
|
#elif defined(_WIN32) || defined(WIN32)
|
||||||
|
#define WINDOWS_NETWORKING
|
||||||
|
#include <conio.h>
|
||||||
|
#include <windows.h>
|
||||||
|
#include <winsock2.h>
|
||||||
|
#include <ws2tcpip.h>
|
||||||
|
#pragma comment(lib, "ws2_32.lib")
|
||||||
|
WSADATA wsaData;
|
||||||
|
#else
|
||||||
|
typedef int SOCKET;
|
||||||
|
#define SYS_SOCKET_NETWORKING
|
||||||
|
#if defined(HW_RVL) && defined(LIBWIISOCKET)
|
||||||
|
#include <wiisocket.h>
|
||||||
|
#endif
|
||||||
|
#include <unistd.h>
|
||||||
|
#include <arpa/inet.h>
|
||||||
|
#include <sys/socket.h>
|
||||||
|
#include <netdb.h>
|
||||||
|
|
||||||
|
#endif
|
||||||
|
using namespace std;
|
||||||
|
|
||||||
|
namespace BoxScript
|
||||||
|
{
|
||||||
|
class Expression;
|
||||||
|
class Stream;
|
||||||
|
class IApplicationState;
|
||||||
|
class ConstantNumber;
|
||||||
|
|
||||||
|
class Expression
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
virtual void DisableScope();
|
||||||
|
virtual string GetNodeName()=0;
|
||||||
|
virtual int64_t Evaluate(IApplicationState* state)=0;
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
class Stream
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
void CopyTo(Stream* strm);
|
||||||
|
virtual int64_t ReadByte();
|
||||||
|
virtual void Write(uint8_t* data,size_t len)=0;
|
||||||
|
virtual size_t Read(uint8_t* data,size_t len)=0;
|
||||||
|
virtual int64_t GetPosition()=0;
|
||||||
|
virtual int64_t GetLength()=0;
|
||||||
|
virtual void SetPosition(int64_t pos)=0;
|
||||||
|
virtual void Flush()=0;
|
||||||
|
virtual void Close()=0;
|
||||||
|
virtual bool CanRead()=0;
|
||||||
|
virtual bool CanWrite()=0;
|
||||||
|
virtual bool CanSeek()=0;
|
||||||
|
|
||||||
|
};
|
||||||
|
class BufferedStream : public Stream
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
Stream* strm;
|
||||||
|
int16_t pos=-1;
|
||||||
|
int16_t readIn=-1;
|
||||||
|
uint8_t buffer[4096];
|
||||||
|
public:
|
||||||
|
BufferedStream(Stream* parent);
|
||||||
|
int64_t ReadByte();
|
||||||
|
void Write(uint8_t* data,size_t len);
|
||||||
|
size_t Read(uint8_t* data,size_t len);
|
||||||
|
int64_t GetPosition();
|
||||||
|
int64_t GetLength();
|
||||||
|
void SetPosition(int64_t pos);
|
||||||
|
void Flush();
|
||||||
|
void Close();
|
||||||
|
bool CanRead();
|
||||||
|
bool CanWrite();
|
||||||
|
bool CanSeek();
|
||||||
|
};
|
||||||
|
class NetworkStream : public Stream
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
SOCKET fd;
|
||||||
|
|
||||||
|
public:
|
||||||
|
|
||||||
|
NetworkStream(SOCKET i);
|
||||||
|
|
||||||
|
void Write(uint8_t* data,size_t len);
|
||||||
|
size_t Read(uint8_t* data,size_t len);
|
||||||
|
int64_t GetPosition();
|
||||||
|
int64_t GetLength();
|
||||||
|
void SetPosition(int64_t pos);
|
||||||
|
void Flush();
|
||||||
|
void Close();
|
||||||
|
bool CanRead();
|
||||||
|
bool CanWrite();
|
||||||
|
bool CanSeek();
|
||||||
|
};
|
||||||
|
typedef int64_t (*internal_func)(IApplicationState* state,vector<Expression*> expressions);
|
||||||
|
class IApplicationState
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
virtual void StopRunning()=0;
|
||||||
|
virtual void ExitIfNotRunning()=0;
|
||||||
|
virtual void AddThreadOwner();
|
||||||
|
virtual void RemoveThreadOwner();
|
||||||
|
virtual void FlushStream(int64_t stream)=0;
|
||||||
|
virtual void DestroyBox(int64_t id)=0;
|
||||||
|
virtual int64_t e2n(Expression* e)=0;
|
||||||
|
virtual Expression* Calln(int64_t e)=0;
|
||||||
|
virtual int64_t CreateStream(Stream* strm)=0;
|
||||||
|
virtual internal_func GetRuntimeFunction(string str)=0;
|
||||||
|
virtual void CopyStream(int64_t strmSrc,int64_t strmDest)=0;
|
||||||
|
|
||||||
|
virtual void CloseStream(int64_t streamId)=0;
|
||||||
|
|
||||||
|
virtual void WriteToStream(int64_t streamId,int64_t boxId,int64_t offset,int64_t len)=0;
|
||||||
|
|
||||||
|
virtual int64_t ReadFromStream(int64_t streamId,int64_t boxId,int64_t offset,int64_t len)=0;
|
||||||
|
virtual int64_t ReadByteFromStream(int64_t streamId)=0;
|
||||||
|
virtual int64_t CreateBufferedStream(int64_t existingStreamId)=0;
|
||||||
|
virtual void SetStreamPosition(int64_t streamId,int64_t streamPos)=0;
|
||||||
|
|
||||||
|
virtual int64_t GetStreamPosition(int64_t streamId)=0;
|
||||||
|
|
||||||
|
virtual int64_t GetStreamLength(int64_t streamId)=0;
|
||||||
|
|
||||||
|
virtual bool CanRead(int64_t streamId)=0;
|
||||||
|
virtual bool CanWrite(int64_t streamId)=0;
|
||||||
|
virtual bool CanSeek(int64_t streamId)=0;
|
||||||
|
|
||||||
|
virtual int64_t ExecuteFunction(string str,vector<Expression*> expressions)=0;
|
||||||
|
virtual bool HasRuntimeFunction(string str)=0;
|
||||||
|
virtual bool HasFunction(string str)=0;
|
||||||
|
virtual void AddFunction(string str,vector<string> args,Expression* exp)=0;
|
||||||
|
virtual void AddRuntimeFunction(string str,internal_func func)=0;
|
||||||
|
virtual string BoxToString(int64_t boxId)=0;
|
||||||
|
virtual void ClearBox(int64_t bId)=0;
|
||||||
|
virtual void AddToBox(int64_t bId,int64_t value)=0;
|
||||||
|
virtual void RemoveFromBox(int64_t bId,int64_t value)=0;
|
||||||
|
virtual void RemoveAtFromBox(int64_t bId,int index)=0;
|
||||||
|
virtual void InsertToBox(int64_t bId,int index,int64_t value)=0;
|
||||||
|
|
||||||
|
virtual void SetBoxValue(int64_t bId,int index,int64_t value)=0;
|
||||||
|
virtual void SetVariable(string name,int64_t value)=0;
|
||||||
|
virtual int64_t GetVariable(string name)=0;
|
||||||
|
|
||||||
|
virtual int64_t BoxLength(int64_t boxId)=0;
|
||||||
|
|
||||||
|
virtual int64_t CreateBox(int len)=0;
|
||||||
|
virtual int64_t CreateBox(string text)=0;
|
||||||
|
virtual int64_t CreateBoxPermanent(string text)=0;
|
||||||
|
virtual int64_t GetBoxValue(int64_t bId, int index)=0;
|
||||||
|
virtual bool HasVariable(string name)=0;
|
||||||
|
|
||||||
|
virtual IApplicationState* NewScope()=0;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
class ApplicationState : public IApplicationState
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
unordered_map<int64_t,pair<vector<int64_t>,bool>> boxes;
|
||||||
|
unordered_map<int64_t,Expression*> expressions;
|
||||||
|
unordered_map<int64_t,Stream*> streams;
|
||||||
|
unordered_map<string,int64_t> variables;
|
||||||
|
unordered_map<string,pair<vector<string>,Expression*>> methods;
|
||||||
|
unordered_map<string,internal_func> runtime_funcs;
|
||||||
|
atomic_int64_t NoBoxes;
|
||||||
|
atomic_int64_t NoStreams;
|
||||||
|
atomic_int64_t NoExpressions;
|
||||||
|
atomic_bool isRunning;
|
||||||
|
|
||||||
|
public:
|
||||||
|
void StopRunning();
|
||||||
|
void ExitIfNotRunning();
|
||||||
|
ApplicationState();
|
||||||
|
internal_func GetRuntimeFunction(string str);
|
||||||
|
void FlushStream(int64_t stream);
|
||||||
|
void DestroyBox(int64_t id);
|
||||||
|
int64_t e2n(Expression* e);
|
||||||
|
Expression* Calln(int64_t e);
|
||||||
|
int64_t CreateStream(Stream* strm);
|
||||||
|
|
||||||
|
void CopyStream(int64_t strmSrc,int64_t strmDest);
|
||||||
|
|
||||||
|
void CloseStream(int64_t streamId);
|
||||||
|
|
||||||
|
void WriteToStream(int64_t streamId,int64_t boxId,int64_t offset,int64_t len);
|
||||||
|
|
||||||
|
int64_t ReadFromStream(int64_t streamId,int64_t boxId,int64_t offset,int64_t len);
|
||||||
|
|
||||||
|
void SetStreamPosition(int64_t streamId,int64_t streamPos);
|
||||||
|
|
||||||
|
int64_t GetStreamPosition(int64_t streamId);
|
||||||
|
|
||||||
|
int64_t GetStreamLength(int64_t streamId);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
bool CanRead(int64_t streamId);
|
||||||
|
bool CanWrite(int64_t streamId);
|
||||||
|
bool CanSeek(int64_t streamId);
|
||||||
|
|
||||||
|
int64_t ExecuteFunction(string str,vector<Expression*> expressions);
|
||||||
|
bool HasRuntimeFunction(string str);
|
||||||
|
bool HasFunction(string str);
|
||||||
|
void AddFunction(string str,vector<string> args,Expression* exp);
|
||||||
|
void AddRuntimeFunction(string str,internal_func func);
|
||||||
|
string BoxToString(int64_t boxId);
|
||||||
|
void ClearBox(int64_t bId);
|
||||||
|
void AddToBox(int64_t bId,int64_t value);
|
||||||
|
void RemoveFromBox(int64_t bId,int64_t value);
|
||||||
|
void RemoveAtFromBox(int64_t bId,int index);
|
||||||
|
void InsertToBox(int64_t bId,int index,int64_t value);
|
||||||
|
int64_t ReadByteFromStream(int64_t streamId);
|
||||||
|
int64_t CreateBufferedStream(int64_t existingStreamId);
|
||||||
|
void SetBoxValue(int64_t bId,int index,int64_t value);
|
||||||
|
void SetVariable(string name,int64_t value);
|
||||||
|
int64_t GetVariable(string name);
|
||||||
|
|
||||||
|
int64_t BoxLength(int64_t boxId);
|
||||||
|
|
||||||
|
int64_t CreateBox(int len);
|
||||||
|
int64_t CreateBox(string text);
|
||||||
|
int64_t CreateBoxPermanent(string text);
|
||||||
|
int64_t GetBoxValue(int64_t bId, int index);
|
||||||
|
bool HasVariable(string name);
|
||||||
|
|
||||||
|
IApplicationState* NewScope();
|
||||||
|
|
||||||
|
private:
|
||||||
|
Stream* GetStream(int64_t id);
|
||||||
|
};
|
||||||
|
class SubscopeApplicationState : public IApplicationState
|
||||||
|
{
|
||||||
|
|
||||||
|
private:
|
||||||
|
atomic_char threads;
|
||||||
|
IApplicationState* state;
|
||||||
|
unordered_map<string,int64_t> variables;
|
||||||
|
public:
|
||||||
|
void StopRunning();
|
||||||
|
void ExitIfNotRunning();
|
||||||
|
void AddThreadOwner();
|
||||||
|
void RemoveThreadOwner();
|
||||||
|
SubscopeApplicationState(IApplicationState* _state);
|
||||||
|
void FlushStream(int64_t stream);
|
||||||
|
void DestroyBox(int64_t id);
|
||||||
|
int64_t e2n(Expression* e);
|
||||||
|
Expression* Calln(int64_t e);
|
||||||
|
int64_t CreateStream(Stream* strm);
|
||||||
|
|
||||||
|
void CopyStream(int64_t strmSrc,int64_t strmDest);
|
||||||
|
|
||||||
|
void CloseStream(int64_t streamId);
|
||||||
|
|
||||||
|
void WriteToStream(int64_t streamId,int64_t boxId,int64_t offset,int64_t len);
|
||||||
|
int64_t ReadByteFromStream(int64_t streamId);
|
||||||
|
int64_t CreateBufferedStream(int64_t existingStreamId);
|
||||||
|
int64_t ReadFromStream(int64_t streamId,int64_t boxId,int64_t offset,int64_t len);
|
||||||
|
|
||||||
|
void SetStreamPosition(int64_t streamId,int64_t streamPos);
|
||||||
|
|
||||||
|
int64_t GetStreamPosition(int64_t streamId);
|
||||||
|
|
||||||
|
int64_t GetStreamLength(int64_t streamId);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
bool CanRead(int64_t streamId);
|
||||||
|
bool CanWrite(int64_t streamId);
|
||||||
|
bool CanSeek(int64_t streamId);
|
||||||
|
|
||||||
|
int64_t ExecuteFunction(string str,vector<Expression*> expressions);
|
||||||
|
internal_func GetRuntimeFunction(string str);
|
||||||
|
bool HasRuntimeFunction(string str);
|
||||||
|
bool HasFunction(string str);
|
||||||
|
void AddFunction(string str,vector<string> args,Expression* exp);
|
||||||
|
void AddRuntimeFunction(string str,internal_func func);
|
||||||
|
string BoxToString(int64_t boxId);
|
||||||
|
void ClearBox(int64_t bId);
|
||||||
|
void AddToBox(int64_t bId,int64_t value);
|
||||||
|
void RemoveFromBox(int64_t bId,int64_t value);
|
||||||
|
void RemoveAtFromBox(int64_t bId,int index);
|
||||||
|
void InsertToBox(int64_t bId,int index,int64_t value);
|
||||||
|
|
||||||
|
void SetBoxValue(int64_t bId,int index,int64_t value);
|
||||||
|
void SetVariable(string name,int64_t value);
|
||||||
|
int64_t GetVariable(string name);
|
||||||
|
|
||||||
|
int64_t BoxLength(int64_t boxId);
|
||||||
|
|
||||||
|
int64_t CreateBox(int len);
|
||||||
|
int64_t CreateBox(string text);
|
||||||
|
int64_t CreateBoxPermanent(string text);
|
||||||
|
int64_t GetBoxValue(int64_t bId, int index);
|
||||||
|
bool HasVariable(string name);
|
||||||
|
|
||||||
|
IApplicationState* NewScope();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
class ConstantNumber : public Expression
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
int64_t num;
|
||||||
|
public:
|
||||||
|
string GetNodeName();
|
||||||
|
ConstantNumber(string num);
|
||||||
|
int64_t Evaluate(IApplicationState* state);
|
||||||
|
};
|
||||||
|
/*public class VariableGetValueNode : Expression
|
||||||
|
{
|
||||||
|
public string Name {get{return var;}}
|
||||||
|
string var;
|
||||||
|
public VariableGetValueNode(string var)
|
||||||
|
{
|
||||||
|
this.var=var;
|
||||||
|
}
|
||||||
|
|
||||||
|
public override long Evaluate(IApplicationState state)
|
||||||
|
{
|
||||||
|
return state.GetVariable(var);
|
||||||
|
}
|
||||||
|
}*/
|
||||||
|
class VariableGetValueNode : public Expression
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
string var;
|
||||||
|
public:
|
||||||
|
string GetName();
|
||||||
|
string GetNodeName();
|
||||||
|
VariableGetValueNode(string var);
|
||||||
|
int64_t Evaluate(IApplicationState* state);
|
||||||
|
};
|
||||||
|
#pragma region "StringNode"
|
||||||
|
class StringNode : public Expression
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
string text;
|
||||||
|
int64_t boxId;
|
||||||
|
public:
|
||||||
|
string GetText();
|
||||||
|
string GetNodeName();
|
||||||
|
StringNode(string var);
|
||||||
|
int64_t Evaluate(IApplicationState* state);
|
||||||
|
|
||||||
|
};
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "SetVariableNode"
|
||||||
|
class SetVariableNode : public Expression
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
Expression* e;
|
||||||
|
string vname;
|
||||||
|
public:
|
||||||
|
~SetVariableNode();
|
||||||
|
string GetNodeName();
|
||||||
|
SetVariableNode(Expression* expression,string name);
|
||||||
|
int64_t Evaluate(IApplicationState* state);
|
||||||
|
};
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "FunctionCallNode"
|
||||||
|
class FunctionCallNode :public Expression
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
string name;
|
||||||
|
vector<Expression*> expressions;
|
||||||
|
public:
|
||||||
|
~FunctionCallNode();
|
||||||
|
string GetNodeName();
|
||||||
|
FunctionCallNode(string _name,vector<Expression*> exps);
|
||||||
|
int64_t Evaluate(IApplicationState* state);
|
||||||
|
|
||||||
|
};
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "AddNode"
|
||||||
|
class AddNode : public Expression
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
~AddNode();
|
||||||
|
Expression* left;
|
||||||
|
Expression* right;
|
||||||
|
string GetNodeName();
|
||||||
|
AddNode(Expression* left,Expression* right);
|
||||||
|
int64_t Evaluate(IApplicationState* state);
|
||||||
|
|
||||||
|
};
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "MinusNode"
|
||||||
|
class MinusNode : public Expression
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
~MinusNode();
|
||||||
|
Expression* left;
|
||||||
|
Expression* right;
|
||||||
|
string GetNodeName();
|
||||||
|
MinusNode(Expression* left,Expression* right);
|
||||||
|
int64_t Evaluate(IApplicationState* state);
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "MultiplyNode"
|
||||||
|
class MultiplyNode : public Expression
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
~MultiplyNode();
|
||||||
|
Expression* left;
|
||||||
|
Expression* right;
|
||||||
|
string GetNodeName();
|
||||||
|
MultiplyNode(Expression* left,Expression* right);
|
||||||
|
int64_t Evaluate(IApplicationState* state);
|
||||||
|
|
||||||
|
};
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "DivideNode"
|
||||||
|
class DivideNode : public Expression
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
~DivideNode();
|
||||||
|
Expression* left;
|
||||||
|
Expression* right;
|
||||||
|
string GetNodeName();
|
||||||
|
DivideNode(Expression* left,Expression* right);
|
||||||
|
int64_t Evaluate(IApplicationState* state);
|
||||||
|
|
||||||
|
};
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "ModulusNode"
|
||||||
|
class ModulusNode : public Expression
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
~ModulusNode();
|
||||||
|
Expression* left;
|
||||||
|
Expression* right;
|
||||||
|
string GetNodeName();
|
||||||
|
ModulusNode(Expression* left,Expression* right);
|
||||||
|
int64_t Evaluate(IApplicationState* state);
|
||||||
|
|
||||||
|
};
|
||||||
|
#pragma endregion
|
||||||
|
#pragma region "ListNode"
|
||||||
|
class ListNode : public Expression
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
~ListNode();
|
||||||
|
bool root;
|
||||||
|
void DisableScope();
|
||||||
|
vector<Expression*> nodes;
|
||||||
|
string GetNodeName();
|
||||||
|
int64_t Evaluate(IApplicationState* state);
|
||||||
|
|
||||||
|
};
|
||||||
|
#pragma endregion
|
||||||
|
|
||||||
|
NetworkStream* TcpClient(string ip,int64_t port);
|
||||||
|
NetworkStream* UdpClient(string ip,int64_t port);
|
||||||
|
|
||||||
|
class ExpressionStream : public Stream
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
IApplicationState* st;
|
||||||
|
vector<Expression*> exp;
|
||||||
|
public:
|
||||||
|
ExpressionStream(IApplicationState* state,vector<Expression*> expressions);
|
||||||
|
void Write(uint8_t* data,size_t len);
|
||||||
|
size_t Read(uint8_t* data,size_t len);
|
||||||
|
int64_t GetPosition();
|
||||||
|
int64_t GetLength();
|
||||||
|
void SetPosition(int64_t pos);
|
||||||
|
void Flush();
|
||||||
|
void Close();
|
||||||
|
bool CanRead();
|
||||||
|
bool CanWrite();
|
||||||
|
bool CanSeek();
|
||||||
|
};
|
||||||
|
class FileStream : public Stream
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
FILE* f;
|
||||||
|
bool cr,cw,cs,own;
|
||||||
|
public:
|
||||||
|
FileStream(FILE* fs,bool canRead,bool canWrite,bool canSeek,bool ownFile);
|
||||||
|
void Write(uint8_t* data,size_t len);
|
||||||
|
size_t Read(uint8_t* data,size_t len);
|
||||||
|
int64_t GetPosition();
|
||||||
|
int64_t GetLength();
|
||||||
|
void SetPosition(int64_t pos);
|
||||||
|
void Flush();
|
||||||
|
void Close();
|
||||||
|
bool CanRead();
|
||||||
|
bool CanWrite();
|
||||||
|
bool CanSeek();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
SOCKET TcpServerInit(string ip,int64_t port);
|
||||||
|
SOCKET UdpServerInit(string ip,int64_t port);
|
||||||
|
|
||||||
|
Stream* AcceptClient(SOCKET fd,string* ip);
|
||||||
|
|
||||||
|
|
||||||
|
void Parse(ListNode* node,vector<Lexer::LexToken> tokens);
|
||||||
|
ListNode* Parse(vector<Lexer::LexToken> tokens);
|
||||||
|
void ParseNode(ListNode* node,vector<Lexer::LexToken> tokens,int* i);
|
||||||
|
void ParseNode(ListNode* node,vector<Lexer::LexToken> tokens,int* i,bool root);
|
||||||
|
Expression* ParseExpression(vector<Lexer::LexToken> tokens,int* i);
|
||||||
|
Expression* ParseTerm(vector<Lexer::LexToken> tokens,int* i);
|
||||||
|
Expression* ParseFactor(vector<Lexer::LexToken> tokens,int* i);int NetworkInit();
|
||||||
|
};
|
||||||
|
|
||||||
|
void RegisterMainRuntimeFunctions(BoxScript::IApplicationState* state);
|
||||||
|
void DestroyApp(int);
|
||||||
|
std::vector<std::string> get_files(std::string path);
|
||||||
|
std::vector<std::string> get_directories(std::string path);
|
||||||
|
|
||||||
|
std::vector<std::pair<std::string,bool>> get_entries(std::string path);
|
||||||
|
|
||||||
|
#if defined(GEKKO)
|
||||||
|
void clear_screen_ogc();
|
||||||
|
#endif
|
|
@ -0,0 +1,47 @@
|
||||||
|
#if !defined(GEKKO)
|
||||||
|
#include "lexer.hpp"
|
||||||
|
#include "parser.hpp"
|
||||||
|
#include <filesystem>
|
||||||
|
namespace fs = std::filesystem;
|
||||||
|
using namespace BoxScript;
|
||||||
|
ListNode* _root_node;
|
||||||
|
std::string read_file(std::string name)
|
||||||
|
{
|
||||||
|
FILE* f=fopen(name.c_str(),"r");
|
||||||
|
std::string text="";
|
||||||
|
while(true)
|
||||||
|
{
|
||||||
|
int read = fgetc(f);
|
||||||
|
if(read == EOF) break;
|
||||||
|
text += (char)read;
|
||||||
|
}
|
||||||
|
fclose(f);
|
||||||
|
return text;
|
||||||
|
}
|
||||||
|
#if !defined(LIBRARY)
|
||||||
|
int main(int argc,char** argv)
|
||||||
|
{
|
||||||
|
if(argc < 2) return 1;
|
||||||
|
_root_node = new BoxScript::ListNode();
|
||||||
|
for(int i = 1;i<argc;i++){
|
||||||
|
std::vector<BoxScript::Lexer::LexToken> tokens=BoxScript::Lexer::Lex(read_file(argv[i]));
|
||||||
|
|
||||||
|
BoxScript::Parse(_root_node,tokens);
|
||||||
|
}
|
||||||
|
BoxScript::ApplicationState* state=new BoxScript::ApplicationState();
|
||||||
|
|
||||||
|
RegisterMainRuntimeFunctions(state);
|
||||||
|
|
||||||
|
_root_node->Evaluate(state);
|
||||||
|
|
||||||
|
DestroyApp(0);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
void DestroyApp(int a)
|
||||||
|
{
|
||||||
|
delete _root_node;
|
||||||
|
exit(a);
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,233 @@
|
||||||
|
|
||||||
|
#if defined(GEKKO)
|
||||||
|
#include "lexer.hpp"
|
||||||
|
#include "parser.hpp"
|
||||||
|
#include <cstdio>
|
||||||
|
#include <cstdlib>
|
||||||
|
#include <gccore.h>
|
||||||
|
#include <dirent.h>
|
||||||
|
#include <sys/stat.h>
|
||||||
|
|
||||||
|
#include <fat.h>
|
||||||
|
#if defined(HW_RVL)
|
||||||
|
#include <wiiuse/wpad.h>
|
||||||
|
#endif
|
||||||
|
#include <ogc/pad.h>
|
||||||
|
static void *xfb = NULL;
|
||||||
|
static GXRModeObj *rmode = NULL;
|
||||||
|
BoxScript::ListNode* _root_node;
|
||||||
|
|
||||||
|
void clear_screen_ogc()
|
||||||
|
{
|
||||||
|
VIDEO_ClearFrameBuffer(rmode,xfb,0);
|
||||||
|
}
|
||||||
|
int appstate=0;
|
||||||
|
std::string read_file(std::string name)
|
||||||
|
{
|
||||||
|
FILE* f=fopen(name.c_str(),"r");
|
||||||
|
std::string text="";
|
||||||
|
while(true)
|
||||||
|
{
|
||||||
|
int read = fgetc(f);
|
||||||
|
if(read == EOF) break;
|
||||||
|
text += (char)read;
|
||||||
|
}
|
||||||
|
fclose(f);
|
||||||
|
return text;
|
||||||
|
}
|
||||||
|
bool DirExists(std::string path)
|
||||||
|
{
|
||||||
|
DIR* dir;
|
||||||
|
bool exists = false;
|
||||||
|
dir = opendir(path.c_str());
|
||||||
|
if(dir != NULL)
|
||||||
|
{
|
||||||
|
exists=true;
|
||||||
|
(void)closedir(dir);
|
||||||
|
}
|
||||||
|
return exists;
|
||||||
|
}
|
||||||
|
|
||||||
|
void LoadSubscripts(BoxScript::ListNode* nodes,std::string path)
|
||||||
|
{
|
||||||
|
std::vector<std::string> files = get_files(path);
|
||||||
|
for(std::string file : files)
|
||||||
|
{
|
||||||
|
std::string newPath = path + "/" + file;
|
||||||
|
std::vector<BoxScript::Lexer::LexToken> tokens=BoxScript::Lexer::Lex(read_file(newPath));
|
||||||
|
BoxScript::Parse(nodes,tokens);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
void PrintElement(std::string text,bool checked)
|
||||||
|
{
|
||||||
|
printf("\t[%c] %s\n",checked ? '*' : ' ', text.c_str());
|
||||||
|
}
|
||||||
|
void LoadScript(BoxScript::ListNode* nodes)
|
||||||
|
{
|
||||||
|
if(!DirExists("/BoxScript"))
|
||||||
|
{
|
||||||
|
mkdir("/BoxScript",0755);
|
||||||
|
}
|
||||||
|
if(DirExists("/BoxScript/Autoboot"))
|
||||||
|
{
|
||||||
|
if(DirExists("/BoxScript/Autoboot/deps"))
|
||||||
|
LoadSubscripts(nodes,"/BoxScript/Autoboot/deps");
|
||||||
|
|
||||||
|
std::vector<BoxScript::Lexer::LexToken> tokens=BoxScript::Lexer::Lex(read_file("/BoxScript/Autoboot/app.bs"));
|
||||||
|
BoxScript::Parse(nodes,tokens);
|
||||||
|
}else{
|
||||||
|
std::vector<std::string> dirs= get_directories("/BoxScript");
|
||||||
|
int item=0;
|
||||||
|
while(appstate != -1)
|
||||||
|
{
|
||||||
|
#if defined(HW_RVL)
|
||||||
|
WPAD_ScanPads();
|
||||||
|
|
||||||
|
#endif
|
||||||
|
PAD_ScanPads();
|
||||||
|
if(PAD_ButtonsDown(0) & PAD_BUTTON_UP)
|
||||||
|
{
|
||||||
|
item--;
|
||||||
|
if(item < 0)
|
||||||
|
{
|
||||||
|
item = dirs.size()-1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(PAD_ButtonsDown(0) & PAD_BUTTON_DOWN)
|
||||||
|
{
|
||||||
|
item++;
|
||||||
|
if(item >= dirs.size())
|
||||||
|
{
|
||||||
|
item=0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(PAD_ButtonsDown(0) & PAD_BUTTON_A)
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
#if defined(HW_RVL)
|
||||||
|
if(WPAD_ButtonsDown(0) & WPAD_BUTTON_UP)
|
||||||
|
{
|
||||||
|
item--;
|
||||||
|
if(item < 0)
|
||||||
|
{
|
||||||
|
item = dirs.size()-1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(WPAD_ButtonsDown(0) & WPAD_BUTTON_DOWN)
|
||||||
|
{
|
||||||
|
item++;
|
||||||
|
if(item >= dirs.size())
|
||||||
|
{
|
||||||
|
item=0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(WPAD_ButtonsDown(0) & WPAD_BUTTON_A)
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
clear_screen_ogc();
|
||||||
|
printf("\x1b[2;2H");
|
||||||
|
printf("\n\n");
|
||||||
|
printf("\tBoxScript 1.0 Wii Version\n");
|
||||||
|
int indexOnScreen = item % 14;
|
||||||
|
int screenOffset = (item - indexOnScreen);
|
||||||
|
int i=0;
|
||||||
|
for(i = 0;i<14;i++)
|
||||||
|
{
|
||||||
|
if(screenOffset + i < dirs.size())
|
||||||
|
PrintElement(dirs[i+screenOffset],i == indexOnScreen);
|
||||||
|
}
|
||||||
|
//printf("\tNo Items: %i",i);
|
||||||
|
VIDEO_WaitVSync();
|
||||||
|
}
|
||||||
|
if(appstate == -1) exit(0);
|
||||||
|
if(DirExists("/BoxScript/" + dirs[item]))
|
||||||
|
LoadSubscripts(nodes,"/BoxScript/" + dirs[item] + "/deps");
|
||||||
|
|
||||||
|
std::vector<BoxScript::Lexer::LexToken> tokens=BoxScript::Lexer::Lex(read_file("/BoxScript/" + dirs[item] + "/app.bs"));
|
||||||
|
BoxScript::Parse(nodes,tokens);
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
BoxScript::ApplicationState* state;
|
||||||
|
void WiiResetPressed(unsigned int a,void* ptr)
|
||||||
|
{
|
||||||
|
if(appstate <= 0)
|
||||||
|
{
|
||||||
|
appstate= -1;
|
||||||
|
}else{
|
||||||
|
state->StopRunning();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
//---------------------------------------------------------------------------------
|
||||||
|
int main(int argc, char **argv) {
|
||||||
|
//---------------------------------------------------------------------------------
|
||||||
|
BoxScript::NetworkInit();
|
||||||
|
fatInitDefault();
|
||||||
|
SYS_SetResetCallback(WiiResetPressed);
|
||||||
|
// Initialise the video system
|
||||||
|
VIDEO_Init();
|
||||||
|
PAD_Init();
|
||||||
|
#if defined(HW_RVL)
|
||||||
|
WPAD_Init();
|
||||||
|
#endif
|
||||||
|
// This function initialises the attached controllers
|
||||||
|
|
||||||
|
|
||||||
|
// Obtain the preferred video mode from the system
|
||||||
|
// This will correspond to the settings in the Wii menu
|
||||||
|
rmode = VIDEO_GetPreferredMode(NULL);
|
||||||
|
|
||||||
|
// Allocate memory for the display in the uncached region
|
||||||
|
xfb = MEM_K0_TO_K1(SYS_AllocateFramebuffer(rmode));
|
||||||
|
|
||||||
|
// Initialise the console, required for printf
|
||||||
|
console_init(xfb,20,20,rmode->fbWidth,rmode->xfbHeight,rmode->fbWidth*VI_DISPLAY_PIX_SZ);
|
||||||
|
|
||||||
|
// Set up the video registers with the chosen mode
|
||||||
|
VIDEO_Configure(rmode);
|
||||||
|
|
||||||
|
// Tell the video hardware where our display memory is
|
||||||
|
VIDEO_SetNextFramebuffer(xfb);
|
||||||
|
|
||||||
|
// Make the display visible
|
||||||
|
VIDEO_SetBlack(FALSE);
|
||||||
|
|
||||||
|
// Flush the video register changes to the hardware
|
||||||
|
VIDEO_Flush();
|
||||||
|
|
||||||
|
// Wait for Video setup to complete
|
||||||
|
VIDEO_WaitVSync();
|
||||||
|
if(rmode->viTVMode&VI_NON_INTERLACE) VIDEO_WaitVSync();
|
||||||
|
|
||||||
|
|
||||||
|
// The console understands VT terminal escape codes
|
||||||
|
// This positions the cursor on row 2, column 0
|
||||||
|
// we can use variables for this with format codes too
|
||||||
|
// e.g. printf ("\x1b[%d;%dH", row, column );
|
||||||
|
printf("\x1b[2;2H");
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
_root_node = new BoxScript::ListNode();
|
||||||
|
LoadScript(_root_node);
|
||||||
|
appstate=1;
|
||||||
|
state=new BoxScript::ApplicationState();
|
||||||
|
RegisterMainRuntimeFunctions(state);
|
||||||
|
|
||||||
|
_root_node->Evaluate(state);
|
||||||
|
|
||||||
|
DestroyApp(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
void DestroyApp(int a)
|
||||||
|
{
|
||||||
|
delete _root_node;
|
||||||
|
exit(a);
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
|
@ -0,0 +1,138 @@
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
# Clear the implicit built in rules
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
.SUFFIXES:
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
ifeq ($(strip $(DEVKITPPC)),)
|
||||||
|
$(error "Please set DEVKITPPC in your environment. export DEVKITPPC=<path to>devkitPPC")
|
||||||
|
endif
|
||||||
|
|
||||||
|
include $(DEVKITPPC)/wii_rules
|
||||||
|
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
# TARGET is the name of the output
|
||||||
|
# BUILD is the directory where object files & intermediate files will be placed
|
||||||
|
# SOURCES is a list of directories containing source code
|
||||||
|
# INCLUDES is a list of directories containing extra header files
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
TARGET := boot
|
||||||
|
BUILD := build
|
||||||
|
SOURCES := ../source
|
||||||
|
DATA := data
|
||||||
|
INCLUDES := include
|
||||||
|
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
# options for code generation
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
CFLAGS = -g -O2 -Wall $(MACHDEP) $(INCLUDE)
|
||||||
|
CXXFLAGS = $(CFLAGS)
|
||||||
|
|
||||||
|
LDFLAGS = -g $(MACHDEP) -Wl,-Map,$(notdir $@).map
|
||||||
|
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
# any extra libraries we wish to link with the project
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
LIBS := -lcurl -lmbedtls -lmbedx509 -lmbedcrypto -lwiisocket -lfat -lwiiuse -lbte -logc -lm
|
||||||
|
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
# list of directories containing libraries, this must be the top level containing
|
||||||
|
# include and lib
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
LIBDIRS := $(PORTLIBS)/wii $(PORTLIBS)/ppc
|
||||||
|
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
# no real need to edit anything past this point unless you need to add additional
|
||||||
|
# rules for different file extensions
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
ifneq ($(BUILD),$(notdir $(CURDIR)))
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
export OUTPUT := $(CURDIR)/$(TARGET)
|
||||||
|
|
||||||
|
export VPATH := $(foreach dir,$(SOURCES),$(CURDIR)/$(dir)) \
|
||||||
|
$(foreach dir,$(DATA),$(CURDIR)/$(dir))
|
||||||
|
|
||||||
|
export DEPSDIR := $(CURDIR)/$(BUILD)
|
||||||
|
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
# automatically build a list of object files for our project
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
CFILES := $(foreach dir,$(SOURCES),$(notdir $(wildcard $(dir)/*.c)))
|
||||||
|
CPPFILES := $(foreach dir,$(SOURCES),$(notdir $(wildcard $(dir)/*.cpp)))
|
||||||
|
sFILES := $(foreach dir,$(SOURCES),$(notdir $(wildcard $(dir)/*.s)))
|
||||||
|
SFILES := $(foreach dir,$(SOURCES),$(notdir $(wildcard $(dir)/*.S)))
|
||||||
|
BINFILES := $(foreach dir,$(DATA),$(notdir $(wildcard $(dir)/*.*)))
|
||||||
|
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
# use CXX for linking C++ projects, CC for standard C
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
ifeq ($(strip $(CPPFILES)),)
|
||||||
|
export LD := $(CC)
|
||||||
|
else
|
||||||
|
export LD := $(CXX)
|
||||||
|
endif
|
||||||
|
|
||||||
|
export OFILES_BIN := $(addsuffix .o,$(BINFILES))
|
||||||
|
export OFILES_SOURCES := $(CPPFILES:.cpp=.o) $(CFILES:.c=.o) $(sFILES:.s=.o) $(SFILES:.S=.o)
|
||||||
|
export OFILES := $(OFILES_BIN) $(OFILES_SOURCES)
|
||||||
|
|
||||||
|
export HFILES := $(addsuffix .h,$(subst .,_,$(BINFILES)))
|
||||||
|
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
# build a list of include paths
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
export INCLUDE := $(foreach dir,$(INCLUDES), -iquote $(CURDIR)/$(dir)) \
|
||||||
|
$(foreach dir,$(LIBDIRS),-I$(dir)/include) \
|
||||||
|
-I$(CURDIR)/$(BUILD) \
|
||||||
|
-I$(LIBOGC_INC)
|
||||||
|
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
# build a list of library paths
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
export LIBPATHS := -L$(LIBOGC_LIB) $(foreach dir,$(LIBDIRS),-L$(dir)/lib)
|
||||||
|
|
||||||
|
export OUTPUT := $(CURDIR)/$(TARGET)
|
||||||
|
.PHONY: $(BUILD) clean
|
||||||
|
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
$(BUILD):
|
||||||
|
@[ -d $@ ] || mkdir -p $@
|
||||||
|
@$(MAKE) --no-print-directory -C $(BUILD) -f $(CURDIR)/Makefile
|
||||||
|
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
clean:
|
||||||
|
@echo clean ...
|
||||||
|
@rm -fr $(BUILD) $(OUTPUT).elf $(OUTPUT).dol
|
||||||
|
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
run:
|
||||||
|
wiiload $(TARGET).dol
|
||||||
|
|
||||||
|
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
else
|
||||||
|
|
||||||
|
DEPENDS := $(OFILES:.o=.d)
|
||||||
|
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
# main targets
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
$(OUTPUT).dol: $(OUTPUT).elf
|
||||||
|
$(OUTPUT).elf: $(OFILES)
|
||||||
|
|
||||||
|
$(OFILES_SOURCES) : $(HFILES)
|
||||||
|
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
# This rule links in binary data with the .jpg extension
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
%.jpg.o %_jpg.h : %.jpg
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
@echo $(notdir $<)
|
||||||
|
$(bin2o)
|
||||||
|
|
||||||
|
-include $(DEPENDS)
|
||||||
|
|
||||||
|
#---------------------------------------------------------------------------------
|
||||||
|
endif
|
||||||
|
#---------------------------------------------------------------------------------
|
|
@ -0,0 +1,10 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
//#define HAVE_LIBSDL2
|
||||||
|
//#define HAVE_LIBCURL
|
||||||
|
|
||||||
|
//#define HAVE_GRRLIB
|
||||||
|
|
||||||
|
#if defined(HW_RVL)
|
||||||
|
#define LIBWIISOCKET
|
||||||
|
#endif
|
Loading…
Reference in New Issue