Imported: AMXXSC, LIBSC, SCASM

This commit is contained in:
David Anderson 2004-08-06 08:46:59 +00:00
parent e2b83f8bf5
commit 06098e3bf1
27 changed files with 4570 additions and 0 deletions

383
compiler/scasm/amx.h Executable file
View File

@ -0,0 +1,383 @@
/* Abstract Machine for the Small compiler
*
* Copyright (c) ITB CompuPhase, 1997-2004
*
* This software is provided "as-is", without any express or implied warranty.
* In no event will the authors be held liable for any damages arising from
* the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software in
* a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#if defined LINUX
#include <sclinux.h>
#endif
#ifndef AMX_H_INCLUDED
#define AMX_H_INCLUDED
#if defined __LCC__ || defined __DMC__ || defined LINUX
#include <stdint.h>
#elif !defined __STDC_VERSION__ || __STDC_VERSION__ < 199901L
/* The ISO C99 defines the int16_t and int_32t types. If the compiler got
* here, these types are probably undefined.
*/
#if defined __FreeBSD__
#include <inttypes.h>
#else
typedef short int int16_t;
typedef unsigned short int uint16_t;
#if defined SN_TARGET_PS2
typedef int int32_t;
typedef unsigned int uint32_t;
#else
typedef long int int32_t;
typedef unsigned long int uint32_t;
#endif
#if defined __WIN32__ || defined _WIN32 || defined WIN32
typedef __int64 int64_t;
typedef unsigned __int64 uint64_t;
#define HAVE_I64
#elif defined __GNUC__
typedef long long int64_t;
typedef unsigned long long uint64_t;
#define HAVE_I64
#endif
#endif
#endif
#if defined __WIN32__ || defined _WIN32 || defined WIN32 /* || defined __MSDOS__ */
#if !defined alloca
#define alloca(n) _alloca(n)
#endif
#endif
#ifdef __cplusplus
extern "C" {
#endif
/* calling convention for native functions */
#if !defined AMX_NATIVE_CALL
#define AMX_NATIVE_CALL
#endif
/* calling convention for all interface functions and callback functions */
#if !defined AMXAPI
#if defined STDECL
#define AMXAPI __stdcall
#elif defined CDECL
#define AMXAPI __cdecl
#else
#define AMXAPI
#endif
#endif
#if !defined AMXEXPORT
#define AMXEXPORT
#endif
/* File format version Required AMX version
* 0 (original version) 0
* 1 (opcodes JUMP.pri, SWITCH and CASETBL) 1
* 2 (compressed files) 2
* 3 (public variables) 2
* 4 (opcodes SWAP.pri/alt and PUSHADDR) 4
* 5 (tagnames table) 4
* 6 (reformatted header) 6
* 7 (name table, opcodes SYMTAG & SYSREQ.D) 7
*/
#define CUR_FILE_VERSION 7 /* current file version; also the current AMX version */
#define MIN_FILE_VERSION 6 /* lowest supported file format version for the current AMX version */
#define MIN_AMX_VERSION 7 /* minimum AMX version needed to support the current file format */
#if defined BIT16
#define SMALL_CELL_SIZE 16 /* for backward compatibility */
#endif
#if !defined SMALL_CELL_SIZE
#define SMALL_CELL_SIZE 32 /* by default, use 32-bit cells */
#endif
#if SMALL_CELL_SIZE==16
typedef uint16_t ucell;
typedef int16_t cell;
#elif SMALL_CELL_SIZE==32
typedef uint32_t ucell;
typedef int32_t cell;
#elif SMALL_CELL_SIZE==64
typedef uint64_t ucell;
typedef int64_t cell;
#else
#error Unsupported cell size (SMALL_CELL_SIZE)
#endif
#define UNPACKEDMAX ((1 << (sizeof(cell)-1)*8) - 1)
struct tagAMX;
typedef cell (AMX_NATIVE_CALL *AMX_NATIVE)(struct tagAMX *amx, cell *params);
typedef int (AMXAPI *AMX_CALLBACK)(struct tagAMX *amx, cell index,
cell *result, cell *params);
typedef int (AMXAPI *AMX_DEBUG)(struct tagAMX *amx);
#if !defined _FAR
#define _FAR
#endif
#if defined _MSC_VER
#pragma warning(disable:4103) /* disable warning message 4103 that complains
* about pragma pack in a header file */
#pragma warning(disable:4100) /* "'%$S' : unreferenced formal parameter" */
#endif
/* Some compilers do not support the #pragma align, which should be fine. Some
* compilers give a warning on unknown #pragmas, which is not so fine...
*/
#if defined SN_TARGET_PS2 || defined __GNUC__
#define AMX_NO_ALIGN
#endif
#if defined __GNUC__
#define PACKED __attribute__((packed))
#else
#define PACKED
#endif
#if !defined AMX_NO_ALIGN
#if defined LINUX
#pragma pack(1) /* structures must be packed (byte-aligned) */
#else
#pragma pack(push)
#pragma pack(1) /* structures must be packed (byte-aligned) */
#if defined __TURBOC__
#pragma option -a- /* "pack" pragma for older Borland compilers */
#endif
#endif
#endif
typedef struct {
const char _FAR *name PACKED;
AMX_NATIVE func PACKED;
} AMX_NATIVE_INFO PACKED;
#define AMX_USERNUM 4
#define sEXPMAX 19 /* maximum name length for file version <= 6 */
#define sNAMEMAX 31 /* maximum name length of symbol name */
typedef struct tagAMX_FUNCSTUB {
uint32_t address PACKED;
char name[sEXPMAX+1] PACKED;
} AMX_FUNCSTUB PACKED;
/* The AMX structure is the internal structure for many functions. Not all
* fields are valid at all times; many fields are cached in local variables.
*/
typedef struct tagAMX {
unsigned char _FAR *base PACKED; /* points to the AMX header ("amxhdr") plus the code, optionally also the data */
unsigned char _FAR *data PACKED; /* points to separate data+stack+heap, may be NULL */
AMX_CALLBACK callback PACKED;
AMX_DEBUG debug PACKED; /* debug callback */
/* for external functions a few registers must be accessible from the outside */
cell cip PACKED; /* instruction pointer: relative to base + amxhdr->cod */
cell frm PACKED; /* stack frame base: relative to base + amxhdr->dat */
cell hea PACKED; /* top of the heap: relative to base + amxhdr->dat */
cell hlw PACKED; /* bottom of the heap: relative to base + amxhdr->dat */
cell stk PACKED; /* stack pointer: relative to base + amxhdr->dat */
cell stp PACKED; /* top of the stack: relative to base + amxhdr->dat */
int flags PACKED; /* current status, see amx_Flags() */
/* for assertions and debug hook */
cell curline PACKED;
cell curfile PACKED;
int dbgcode PACKED;
cell dbgaddr PACKED;
cell dbgparam PACKED;
char _FAR *dbgname PACKED;
/* user data */
long usertags[AMX_USERNUM] PACKED;
void _FAR *userdata[AMX_USERNUM] PACKED;
/* native functions can raise an error */
int error PACKED;
/* the sleep opcode needs to store the full AMX status */
cell pri PACKED;
cell alt PACKED;
cell reset_stk PACKED;
cell reset_hea PACKED;
cell sysreq_d PACKED; /* relocated address/value for the SYSREQ.D opcode */
#if defined JIT
/* support variables for the JIT */
int reloc_size PACKED; /* required temporary buffer for relocations */
long code_size PACKED; /* estimated memory footprint of the native code */
#endif
} AMX PACKED;
/* The AMX_HEADER structure is both the memory format as the file format. The
* structure is used internaly.
*/
typedef struct tagAMX_HEADER {
int32_t size PACKED; /* size of the "file" */
uint16_t magic PACKED; /* signature */
char file_version PACKED; /* file format version */
char amx_version PACKED; /* required version of the AMX */
int16_t flags PACKED;
int16_t defsize PACKED; /* size of a definition record */
int32_t cod PACKED; /* initial value of COD - code block */
int32_t dat PACKED; /* initial value of DAT - data block */
int32_t hea PACKED; /* initial value of HEA - start of the heap */
int32_t stp PACKED; /* initial value of STP - stack top */
int32_t cip PACKED; /* initial value of CIP - the instruction pointer */
int32_t publics PACKED; /* offset to the "public functions" table */
int32_t natives PACKED; /* offset to the "native functions" table */
int32_t libraries PACKED; /* offset to the table of libraries */
int32_t pubvars PACKED; /* the "public variables" table */
int32_t tags PACKED; /* the "public tagnames" table */
int32_t nametable PACKED; /* name table, file version 7 only */
} AMX_HEADER PACKED;
#define AMX_MAGIC 0xf1e0
enum {
AMX_ERR_NONE,
/* reserve the first 15 error codes for exit codes of the abstract machine */
AMX_ERR_EXIT, /* forced exit */
AMX_ERR_ASSERT, /* assertion failed */
AMX_ERR_STACKERR, /* stack/heap collision */
AMX_ERR_BOUNDS, /* index out of bounds */
AMX_ERR_MEMACCESS, /* invalid memory access */
AMX_ERR_INVINSTR, /* invalid instruction */
AMX_ERR_STACKLOW, /* stack underflow */
AMX_ERR_HEAPLOW, /* heap underflow */
AMX_ERR_CALLBACK, /* no callback, or invalid callback */
AMX_ERR_NATIVE, /* native function failed */
AMX_ERR_DIVIDE, /* divide by zero */
AMX_ERR_SLEEP, /* go into sleepmode - code can be restarted */
AMX_ERR_MEMORY = 16, /* out of memory */
AMX_ERR_FORMAT, /* invalid file format */
AMX_ERR_VERSION, /* file is for a newer version of the AMX */
AMX_ERR_NOTFOUND, /* function not found */
AMX_ERR_INDEX, /* invalid index parameter (bad entry point) */
AMX_ERR_DEBUG, /* debugger cannot run */
AMX_ERR_INIT, /* AMX not initialized (or doubly initialized) */
AMX_ERR_USERDATA, /* unable to set user data field (table full) */
AMX_ERR_INIT_JIT, /* cannot initialize the JIT */
AMX_ERR_PARAMS, /* parameter error */
AMX_ERR_DOMAIN, /* domain error, expression result does not fit in range */
};
enum {
DBG_INIT, /* query/initialize */
DBG_FILE, /* file number in curfile, filename in name */
DBG_LINE, /* line number in curline, file number in curfile */
DBG_SYMBOL, /* address in dbgaddr, class/type in dbgparam */
DBG_CLRSYM, /* stack address below which locals should be removed. stack address in stk */
DBG_CALL, /* function call, address jumped to in dbgaddr */
DBG_RETURN, /* function returns */
DBG_TERMINATE, /* program ends, code address in dbgaddr, reason in dbgparam */
DBG_SRANGE, /* symbol size and dimensions (arrays); level in dbgaddr (!); length in dbgparam */
DBG_SYMTAG, /* tag of the most recent symbol (if non-zero), tag in dbgparam */
};
/* AMX_FLAG_CHAR16 0x01 no longer used */
#define AMX_FLAG_DEBUG 0x02 /* symbolic info. available */
#define AMX_FLAG_COMPACT 0x04 /* compact encoding */
#define AMX_FLAG_BIGENDIAN 0x08 /* big endian encoding */
#define AMX_FLAG_NOCHECKS 0x10 /* no array bounds checking */
#define AMX_FLAG_BROWSE 0x4000 /* browsing/relocating or executing */
#define AMX_FLAG_RELOC 0x8000 /* jump/call addresses relocated */
#define AMX_EXEC_MAIN -1 /* start at program entry point */
#define AMX_EXEC_CONT -2 /* continue from last address */
#define AMX_USERTAG(a,b,c,d) ((a) | ((b)<<8) | ((long)(c)<<16) | ((long)(d)<<24))
#define AMX_EXPANDMARGIN 64
/* for native functions that use floating point parameters, the following
* two macros are convenient for casting a "cell" into a "float" type _without_
* changing the bit pattern
*/
#if SMALL_CELL_SIZE==32
#define amx_ftoc(f) ( * ((cell*)&f) ) /* float to cell */
#define amx_ctof(c) ( * ((float*)&c) ) /* cell to float */
#elif SMALL_CELL_SIZE==64
#define amx_ftoc(f) ( * ((cell*)&f) ) /* float to cell */
#define amx_ctof(c) ( * ((double*)&c) ) /* cell to float */
#else
#error Unsupported cell size
#endif
#define amx_StrParam(amx,param,result) \
do { \
cell *amx_cstr_; int amx_length_; \
amx_GetAddr((amx), (param), &amx_cstr_); \
amx_StrLen(amx_cstr_, &amx_length_); \
if (amx_length_ > 0 && \
((result) = (void*)alloca((amx_length_ + 1) * sizeof(*(result)))) != NULL) \
amx_GetString((char*)(result), amx_cstr_, sizeof(*(result))>1); \
else (result) = NULL; \
} while (0)
uint16_t * AMXAPI amx_Align16(uint16_t *v);
uint32_t * AMXAPI amx_Align32(uint32_t *v);
#if defined _I64_MAX || defined HAVE_I64
uint64_t * AMXAPI amx_Align64(uint64_t *v);
#endif
int AMXAPI amx_Allot(AMX *amx, int cells, cell *amx_addr, cell **phys_addr);
int AMXAPI amx_Callback(AMX *amx, cell index, cell *result, cell *params);
int AMXAPI amx_Cleanup(AMX *amx);
int AMXAPI amx_Clone(AMX *amxClone, AMX *amxSource, void *data);
int AMXAPI amx_Debug(AMX *amx); /* default debug procedure, does nothing */
int AMXAPI amx_Exec(AMX *amx, cell *retval, int index, int numparams, ...);
int AMXAPI amx_Execv(AMX *amx, cell *retval, int index, int numparams, cell params[]);
int AMXAPI amx_FindNative(AMX *amx, const char *name, int *index);
int AMXAPI amx_FindPublic(AMX *amx, const char *funcname, int *index);
int AMXAPI amx_FindPubVar(AMX *amx, const char *varname, cell *amx_addr);
int AMXAPI amx_FindTagId(AMX *amx, cell tag_id, char *tagname);
int AMXAPI amx_Flags(AMX *amx,uint16_t *flags);
int AMXAPI amx_GetAddr(AMX *amx,cell amx_addr,cell **phys_addr);
int AMXAPI amx_GetNative(AMX *amx, int index, char *funcname);
int AMXAPI amx_GetPublic(AMX *amx, int index, char *funcname);
int AMXAPI amx_GetPubVar(AMX *amx, int index, char *varname, cell *amx_addr);
int AMXAPI amx_GetString(char *dest,const cell *source, int use_wchar);
int AMXAPI amx_GetTag(AMX *amx, int index, char *tagname, cell *tag_id);
int AMXAPI amx_GetUserData(AMX *amx, long tag, void **ptr);
int AMXAPI amx_Init(AMX *amx, void *program);
int AMXAPI amx_InitJIT(AMX *amx, void *reloc_table, void *native_code);
int AMXAPI amx_MemInfo(AMX *amx, long *codesize, long *datasize, long *stackheap);
int AMXAPI amx_NameLength(AMX *amx, int *length);
AMX_NATIVE_INFO * AMXAPI amx_NativeInfo(const char *name,AMX_NATIVE func);
int AMXAPI amx_NumNatives(AMX *amx, int *number);
int AMXAPI amx_NumPublics(AMX *amx, int *number);
int AMXAPI amx_NumPubVars(AMX *amx, int *number);
int AMXAPI amx_NumTags(AMX *amx, int *number);
int AMXAPI amx_RaiseError(AMX *amx, int error);
int AMXAPI amx_Register(AMX *amx, AMX_NATIVE_INFO *nativelist, int number);
int AMXAPI amx_Release(AMX *amx, cell amx_addr);
int AMXAPI amx_SetCallback(AMX *amx, AMX_CALLBACK callback);
int AMXAPI amx_SetDebugHook(AMX *amx, AMX_DEBUG debug);
int AMXAPI amx_SetString(cell *dest, const char *source, int pack, int use_wchar);
int AMXAPI amx_SetUserData(AMX *amx, long tag, void *ptr);
int AMXAPI amx_StrLen(cell *cstring, int *length);
int AMXAPI amx_UTF8Get(const char *string, const char **endptr, cell *value);
int AMXAPI amx_UTF8Put(char *string, char **endptr, int maxchars, cell value);
int AMXAPI amx_UTF8Check(const char *string);
#if !defined AMX_NO_ALIGN
#if defined LINUX
#pragma pack() /* reset default packing */
#else
#pragma pack(pop) /* reset previous packing */
#endif
#endif
#ifdef __cplusplus
}
#endif
#endif /* AMX_H_INCLUDED */

1743
compiler/scasm/amx_compiler.cpp Executable file

File diff suppressed because it is too large Load Diff

90
compiler/scasm/amx_compiler.h Executable file
View File

@ -0,0 +1,90 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#ifndef _INCLUDE_AMXCOMPILER_H
#define _INCLUDE_AMXCOMPILER_H
typedef enum
{
Token_None,
Token_Or,
Token_Xor,
Token_And,
Token_Shr,
Token_Shl,
Token_Mod,
Token_Div,
Token_Mul,
Token_Sub,
Token_Add,
Token_Not,
/* End */
Tokens_Total,
} OpToken;
class rpn
{
public:
//TODO: use linked lists, but not std::list
std::vector<char> ops;
std::vector<int> vals;
};
class Compiler
{
public:
Compiler();
~Compiler();
Compiler(std::string &f);
void Load(std::string &f);
bool Parse();
bool Compile();
int CurLine() { return curLine; }
ErrorMngr *ErrorHandler() { return CError; }
public:
int FindArguments(std::string &text, std::vector<std::string*> &List, int &end, bool simple = false);
private:
void ProcessDirective(std::string &text);
void Init();
void InitOpcodes();
int Eval(std::string &str, SymbolType sym = Sym_None);
int EvalRpn(rpn *r, SymbolType sym);
OpToken OperToken(char c);
char OperChar(OpToken c);
private:
std::vector<Asm *> CodeList;
std::map<std::string,int> OpCodes;
ErrorMngr *CError;
SymbolList *CSymbols;
DefineMngr *CDefines;
MacroList *CMacros;
DataMngr *DAT;
ProcMngr *PROC;
LabelMngr *CLabels;
NativeMngr *CNatives;
std::string filename;
int curLine;
int lastCip;
int cellsize;
};
#endif //_INCLUDE_AMXCOMPILER_H

87
compiler/scasm/amx_data.cpp Executable file
View File

@ -0,0 +1,87 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#include "amxasm.h"
DataMngr::~DataMngr()
{
std::vector<DataMngr::Datum *>::iterator i;
for (i=List.begin(); i!=List.end(); i++)
{
if ( (*i) )
delete (*i);
}
List.clear();
}
DataMngr::Datum::Datum()
{
db = false;
offset = -1;
}
void DataMngr::Add(std::string &s, CExpr &expr, bool db)
{
DataMngr::Datum *D = new DataMngr::Datum();
D->symbol.assign(s);
D->e = expr;
if (List.size() == 0)
{
D->offset = 0;
} else {
DataMngr::Datum *p = List[List.size()-1];
D->offset = p->offset +
((p->e.GetType() == Val_Number) ?
cellsize : p->e.Size() * cellsize);
}
}
DataMngr::Datum *DataMngr::FindData(std::string &sym)
{
std::vector<DataMngr::Datum *>::iterator i;
for (i=List.begin(); i!=List.end(); i++)
{
if ((*i)->symbol.compare(sym) == 0)
{
return (*i);
}
}
return NULL;
}
int DataMngr::GetOffset(std::string &sym)
{
DataMngr::Datum *D = NULL;
D = FindData(sym);
if (D == NULL)
return DataMngr::nof;
return D->offset;
}

52
compiler/scasm/amx_data.h Executable file
View File

@ -0,0 +1,52 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#ifndef _INCLUDE_AMXDATA_H
#define _INCLUDE_AMXDATA_H
class DataMngr
{
public:
class Datum
{
public:
Datum();
std::string symbol;
CExpr e;
bool db;
int offset;
};
public:
~DataMngr();
DataMngr() { cellsize = 4; lastOffset = 0; }
DataMngr(int cell) { lastOffset = 0; cellsize = cell; }
void Add(std::string &s, CExpr &expr, bool db = false);
DataMngr::Datum *FindData(std::string &sym);
int GetOffset(std::string &sym);
private:
std::vector<DataMngr::Datum *> List;
int lastOffset;
int cellsize;
static const int nof = -1;
};
#endif //_INCLUDE_AMXDATA_H

84
compiler/scasm/amx_define.cpp Executable file
View File

@ -0,0 +1,84 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#include "amxasm.h"
DefineMngr::~DefineMngr()
{
std::vector<DefineMngr::Define *>::iterator i;
for (i=List.begin(); i!=List.end(); i++)
{
if ( (*i) )
delete (*i);
}
List.clear();
}
void DefineMngr::Define::Set(std::string &s, std::string &d)
{
sym.assign(s);
def.assign(d);
}
DefineMngr::Define *DefineMngr::AddDefine(std::string &sym, std::string &def)
{
DefineMngr::Define *D = new DefineMngr::Define;
D->Set(sym, def);
List.push_back(D);
return D;
}
DefineMngr::Define *DefineMngr::FindDefine(std::string &sym)
{
std::vector<DefineMngr::Define*>::iterator i;
for (i=List.begin(); i!=List.end(); i++)
{
if ((*i)->GetSymbol()->compare(sym)==0)
{
return (*i);
}
}
return NULL;
}
void DefineMngr::SearchAndReplace(std::string &text)
{
std::vector<DefineMngr::Define*>::iterator i;
DefineMngr::Define *D = NULL;
int pos;
for (i=List.begin(); i!=List.end(); i++)
{
D = (*i);
pos = FindSymbol(text, *(D->GetSymbol()), 0);
if (pos != -1)
{
text.replace(pos, D->GetSymbol()->size(), *(D->GetDefine()));
i = List.begin();
}
}
}

48
compiler/scasm/amx_define.h Executable file
View File

@ -0,0 +1,48 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#ifndef _INCLUDE_DEFINE_H
#define _INCLUDE_DEFINE_H
class DefineMngr
{
public:
class Define
{
public:
void Set(std::string &s, std::string &d);
const std::string *GetSymbol() { return &sym; }
const std::string *GetDefine() { return &def; }
private:
std::string sym;
std::string def;
};
private:
std::vector<Define *> List;
public:
~DefineMngr();
DefineMngr::Define *AddDefine(std::string &sym, std::string &def);
DefineMngr::Define *FindDefine(std::string &sym);
void SearchAndReplace(std::string &text);
};
#endif //_INCLUDE_DEFINE_H

127
compiler/scasm/amx_error.cpp Executable file
View File

@ -0,0 +1,127 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#include "amxasm.h"
ErrorMngr::ErrorMngr()
{
printf("Not instantiated with a compiler.");
exit(0);
}
ErrorMngr::ErrorMngr(void *c)
{
Cmp = c;
DefineErrors();
Totals[0] = 0;
Totals[1] = 0;
Totals[2] = 0;
Totals[3] = 0;
}
ErrorType ErrorMngr::GetErrorType(ErrorCode id)
{
if (id > fatals_start && id < fatals_end)
return Err_Fatal;
if (id > warnings_start && id < warnings_end)
return Err_Warning;
if (id > notices_start && id < notices_end)
return Err_Notice;
if (id > errors_start && id < errors_end)
return Err_Error;
return Err_None;
}
void ErrorMngr::DefineErrors()
{
List.resize(fatals_end+1);
List.at(Warning_Hex_Start) = "Hexadecimal notation is 0xN, 0 missing";
List.at(Warning_Null_Expression) = "Bad expression will evaluate to 0";
List.at(Err_String_Terminate) = "String not terminated properly";
List.at(Err_String_Extra) = "Unexpected characters after string end (character '%c')";
List.at(Err_Unexpected_Char) = "Unexpected character found (character '%c')";
List.at(Err_Wandering_Stuff) = "Unknown directive placed outside of a section";
List.at(Err_Symbol_Reuse) = "Symbol \"%s\" already defined on line %d";
List.at(Err_Invalid_Stor) = "Invalid DAT storage identifier \"%s\"";
List.at(Err_Unknown_Symbol) = "Unknown symbol \"%s\"";
List.at(Err_Symbol_Type) = "Expected symbol type %d, got %d (bad symbol)";
List.at(Err_Invalid_Symbol) = "Invalid symbol";
List.at(Err_Opcode) = "Invalid or unrecognized opcode";
List.at(Err_Unmatched_Token) = "Unmatched token '%c'";
List.at(Err_FileNone) = "No file specified";
List.at(Err_FileOpen) = "Could not open file \"%s\"";
List.at(Err_NoMemory) = "Ran out of memory";
List.at(Err_PragmaStacksize) = "Invalid stacksize on #pragma stacksize";
List.at(Err_InvalidMacro) = "Invalid or empty macro definition";
List.at(Err_SymbolRedef) = "Symbol \"%s\" already defined on line %d";
List.at(Err_Reserved) = "Symbol assigned to a reserved token";
List.at(Err_MacroParamCount) = "Parameter count for macro \"%s\" incorrect";
List.at(Err_FatalTokenError) = "Fatal token error encountered";
List.at(Err_Invalid_Section) = "Section identifier \"%s\" is not valid, ignoring section.";
HighestError = Err_None;
}
void ErrorMngr::ErrorMsg(ErrorCode error, ...)
{
static char *ErrorSwi[4] = {"Notice", "Warning", "Error", "Fatal Error"};
static char errbuf[1024];
ErrorType type = GetErrorType(error);
if (type == -1)
return;
va_list argptr;
va_start(argptr, error);
if (((Compiler *)Cmp)->CurLine() == -1)
sprintf(errbuf, "%s(%d): %s\n", ErrorSwi[type], error, GetError(error));
else
sprintf(errbuf, "%s(%d) on line %d: %s\n", ErrorSwi[type], error, ((Compiler *)Cmp)->CurLine(), GetError(error));
vprintf(errbuf, argptr);
va_end(argptr);
Totals[type]++;
if (type == Err_Fatal)
exit(0);
if (type > HighestError)
HighestError = type;
}
const char *ErrorMngr::GetError(ErrorCode id)
{
if (id == fatals_start || id == fatals_end)
return NULL;
if (id == warnings_start || id == warnings_end)
return NULL;
if (id == notices_start || id == notices_end)
return NULL;
if (id == errors_start || id == errors_end)
return NULL;
if (id < notices_start || id > fatals_end)
return NULL;
return List.at(id);
}

92
compiler/scasm/amx_error.h Executable file
View File

@ -0,0 +1,92 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#ifndef _INCLUDE_AMX_ERROR
#define _INCLUDE_AMX_ERROR
typedef enum
{
Err_None=-1,
Err_Notice,
Err_Warning,
Err_Error,
Err_Fatal,
} ErrorType;
typedef enum
{
notices_start,
notices_end,
warnings_start,
Warning_Hex_Start,
Warning_Null_Expression,
warnings_end,
errors_start,
Err_String_Terminate,
Err_String_Extra,
Err_Unexpected_Char,
Err_Invalid_Section,
Err_Wandering_Stuff,
Err_Symbol_Reuse, /* Non-fatal version of Redef */
Err_Invalid_Stor,
Err_Unknown_Symbol,
Err_Symbol_Type,
Err_Invalid_Symbol,
Err_Opcode,
Err_Unmatched_Token,
errors_end,
fatals_start,
Err_FileNone,
Err_FileOpen,
Err_NoMemory,
Err_PragmaStacksize,
Err_InvalidMacro,
Err_SymbolRedef,
Err_Reserved,
Err_MacroParamCount,
Err_FatalTokenError,
fatals_end,
} ErrorCode;
class ErrorMngr
{
private:
void DefineErrors();
const char *GetError(ErrorCode id);
ErrorType GetErrorType(ErrorCode id);
private:
std::vector<const char *> List;
ErrorType HighestError;
void *Cmp;
int Totals[4];
public:
ErrorMngr();
ErrorMngr(void *c);
void ErrorMsg(ErrorCode error, ...);
ErrorType GetStatus() { return HighestError; }
};
#endif //_INCLUDE_AMX_ERROR

73
compiler/scasm/amx_label.cpp Executable file
View File

@ -0,0 +1,73 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#include "amxasm.h"
LabelMngr::~LabelMngr()
{
std::vector<LabelMngr::Label *>::iterator i;
for (i=List.begin(); i!=List.end(); i++)
{
if ( (*i) )
delete (*i);
}
List.clear();
}
void LabelMngr::AddLabel(SymbolList::Symbol *sym, int cip)
{
LabelMngr::Label *p = new LabelMngr::Label;
p->sym = sym;
p->cip = cip;
List.push_back(p);
}
LabelMngr::Label *LabelMngr::FindLabel(std::string &sym)
{
std::vector<LabelMngr::Label *>::iterator i;
for (i=List.begin(); i!=List.end(); i++)
{
if ( (*i)->sym->IsEqual(sym) )
{
return (*i);
}
}
return NULL;
}
int LabelMngr::GetCip(std::string &sym)
{
LabelMngr::Label *p = NULL;
p = FindLabel(sym);
if (p == NULL)
return ncip;
return p->cip;
}

46
compiler/scasm/amx_label.h Executable file
View File

@ -0,0 +1,46 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#ifndef _INCLUDE_AMXLABEL_H
#define _INCLUDE_AMXLABEL_H
class LabelMngr
{
public:
class Label
{
public:
SymbolList::Symbol *sym;
int cip;
};
public:
~LabelMngr();
void AddLabel(SymbolList::Symbol *sym, int cip);
LabelMngr::Label *FindLabel(std::string &sym);
int GetCip(std::string &sym);
private:
std::vector<LabelMngr::Label *> List;
public:
static const int ncip = -1;
};
#endif //_INCLUDE_AMXLABEL_H

167
compiler/scasm/amx_macro.cpp Executable file
View File

@ -0,0 +1,167 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#include "amxasm.h"
MacroList::~MacroList()
{
std::vector<MacroList::Macro *>::iterator i;
for (i=List.begin(); i!=List.end(); i++)
{
if ( (*i) )
delete (*i);
}
List.clear();
}
MacroList::Macro::~Macro()
{
std::vector<std::string *>::iterator i;
for (i=argList.begin(); i!=argList.end(); i++)
{
if ( (*i) )
delete (*i);
}
argList.clear();
}
MacroList::MacroList()
{
printf("Not instantiated with a compiler\n");
exit(0);
}
MacroList::MacroList(void *c)
{
CError = ((Compiler *)c)->ErrorHandler();
Cmp = c;
}
std::string *MacroList::BeginReplacement(MacroList::Macro *macro)
{
std::string *mstring = new std::string(macro->macro);
macro->arg = macro->argList.begin();
macro->argpos = 0;
return mstring;
}
int MacroList::ReplaceArgument(MacroList::Macro *m, std::string *macro, std::string &arg, int pos = 0)
{
int i = 0, bPos = 0;
bPos = FindSymbol(*macro, *(*m->arg), pos);
if (bPos != -1)
{
macro->replace(bPos, (*m->arg)->size(), arg);
bPos += (int)arg.size();
}
m->arg++;
m->argpos++;
return bPos;
}
void MacroList::EndReplacement(MacroList::Macro *m, std::string *macro)
{
if (m->arg != m->argList.end())
{
CError->ErrorMsg(Err_MacroParamCount, m->symbol.c_str());
}
m->arg = m->argList.begin();
m->argpos = 0;
}
MacroList::Macro *MacroList::AddMacroBegin(std::string &symbol, std::string &mac)
{
Macro *macro = new Macro;
macro->macro.assign(mac);
macro->symbol.assign(symbol);
return macro;
}
void MacroList::AddMacroArgument(MacroList::Macro *m, std::string &arg)
{
std::string *sArg = new std::string(arg);
m->argList.push_back(sArg);
}
void MacroList::AddMacroEnd(MacroList::Macro *m)
{
List.push_back(m);
}
MacroList::Macro *MacroList::FindMacro(std::string &sym)
{
std::vector<Macro *>::iterator i;
for (i=List.begin(); i!=List.end(); i++)
{
if ((*i)->macro.compare(sym) == 0)
return (*i);
}
return NULL;
}
void MacroList::SearchAndReplace(std::string &text)
{
std::vector<Macro *>::iterator i;
MacroList::Macro *m = NULL;
int pos=0, symPos=0, bPos=0, argPos=0;
for (i=List.begin(); i!=List.end(); i++)
{
m = (*i);
pos = FindSymbol(text, m->symbol, 0);
if (pos != -1)
{
/* Strip the arguments */
std::string argstring;
symPos = pos + (int)m->symbol.size();
argstring.assign(text.substr(symPos+1, text.size()-symPos));
std::vector<std::string *> argList;
((Compiler *)Cmp)->FindArguments(argstring, argList, bPos);
/* Build the macro */
std::string *ms;
ms = BeginReplacement(m);
std::vector<std::string *>::iterator j;
for (j=argList.begin(); j!=argList.end(); j++)
{
argPos = ReplaceArgument(m, ms, *(*j), argPos);
}
EndReplacement(m, ms);
/* Search and replace */
text.replace(pos, bPos-pos, *ms);
/* Cleanup */
delete ms;
i = List.begin();
}
}
}

57
compiler/scasm/amx_macro.h Executable file
View File

@ -0,0 +1,57 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#ifndef _INCLUDE_MACRO_H
#define _INCLUDE_MACRO_H
class MacroList
{
public:
class Macro
{
public:
~Macro();
std::vector<std::string*>::iterator arg;
std::vector<std::string*> argList;
std::string symbol;
std::string macro;
int argpos;
};
public:
MacroList();
MacroList(void *c);
~MacroList();
MacroList::Macro *AddMacroBegin(std::string &symbol, std::string &mac);
void AddMacroArgument(MacroList::Macro *m, std::string &arg);
void AddMacroEnd(MacroList::Macro *m);
MacroList::Macro *FindMacro(std::string &sym);
std::string *BeginReplacement(MacroList::Macro *macro);
int ReplaceArgument(MacroList::Macro *m, std::string *macro, std::string &arg, int pos);
void EndReplacement(MacroList::Macro *m, std::string *macro);
void SearchAndReplace(std::string &text);
private:
std::vector<Macro *> List;
ErrorMngr *CError;
void *Cmp;
};
#endif //_INCLUDE_MACRO_H

78
compiler/scasm/amx_natives.cpp Executable file
View File

@ -0,0 +1,78 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#include "amxasm.h"
NativeMngr::~NativeMngr()
{
std::vector<NativeMngr::Native *>::iterator i;
for (i=List.begin(); i!=List.end(); i++)
{
if ( (*i) )
delete (*i);
}
List.clear();
}
void NativeMngr::AddNative(SymbolList::Symbol *S)
{
NativeMngr::Native *N = new NativeMngr::Native;
N->S = S;
N->used = false;
List.push_back(N);
}
int NativeMngr::GetNativeId(std::string &sym)
{
int pos = 0;
std::vector<NativeMngr::Native *>::iterator i;
for (i=List.begin(); i!=List.end(); i++)
{
if ( (*i)->S->IsEqual(sym) )
{
return pos;
}
pos++;
}
return ncip;
}
NativeMngr::Native *NativeMngr::FindNative(std::string &sym)
{
std::vector<NativeMngr::Native *>::iterator i;
for (i=List.begin(); i!=List.end(); i++)
{
if ( (*i)->S->IsEqual(sym) )
{
return (*i);
}
}
return NULL;
}

47
compiler/scasm/amx_natives.h Executable file
View File

@ -0,0 +1,47 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#ifndef _INCLUDE_NATIVES_H
#define _INCLUDE_NATIVES_H
class NativeMngr
{
public:
class Native
{
public:
Native() { used = false; S = NULL; }
SymbolList::Symbol *S;
bool used;
};
public:
~NativeMngr();
void AddNative(SymbolList::Symbol *S);
NativeMngr::Native *FindNative(std::string &sym);
int GetNativeId(std::string &sym);
public:
static const int ncip = -1;
private:
std::vector<NativeMngr::Native *> List;
};
#endif //_INCLUDE_NATIVES_H

187
compiler/scasm/amx_parser.cpp Executable file
View File

@ -0,0 +1,187 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#include "amxasm.h"
char isletter(char c)
{
if (c >= 65 && c <= 90)
return c;
if (c >= 97 && c <= 122)
return c;
if (c == '_')
return c;
return 0;
}
char expr(char c)
{
if (c == '(')
return ')';
if (c == ')')
return '(';
return 0;
}
char literal(char c)
{
if (c == '"')
return '"';
if (c == '\'')
return '\'';
return 0;
}
void StripComments(std::string &text)
{
size_t i = 0;
char c = 0, l = 0;
for (i=0; i<text.size(); i++)
{
c = text[i];
if (literal(c))
{
if (!l)
{
l = c;
} else {
l = 0;
}
} else {
if (!l)
{
if (c == ';')
{
text.erase(i, text.size()-i);
return;
}
}
}
}
}
void StringBreak(std::string &Source, std::string &Left, std::string &Right)
{
int done_flag = 0;
int l=0;
unsigned int i=0;
for (i=0; i<Source.size(); i++)
{
if (isspace(Source[i]) && !done_flag)
{
while (isspace(Source[++i]));
done_flag = 1;
}
if (!done_flag)
{
Left.push_back(Source[i]);
} else {
Right.push_back(Source[i]);
}
}
}
/* Strips whitespace from the beginning and end of a string */
void Strip(std::string &text)
{
int i = 0;
for (i=0; i<(int)text.size(); i++)
{
if (!isspace(text[i]))
{
if (i!=0)
{
text.erase(0, i);
}
break;
}
}
if (text.size() < 1)
return;
for (i=(int)(text.size()-1); i>=0; i--)
{
if (!isspace(text[i]))
{
if (i != (int)(text.size() - 1))
{
text.erase(i+1, text.size()-1-i);
}
break;
}
}
}
/* This is a very simple symbol searcher
* It only restricts the pattern location to outside of
* string literals and other symbols.
*/
int FindSymbol(std::string &text, const std::string &sym, int startPos = 0)
{
unsigned int i = 0;
char c = 0, d = 0, l = 0;
for (i=startPos; i<text.size(); i++)
{
d = text[i];
/* If the string can't possibly fit, opt out */
if (sym.size() > text.size() - i)
break;
/* Skip literal strings */
if (l)
{
if (d == l)
l = 0;
c = d;
continue;
} else {
l = literal(d);
if (l)
{
c = d;
continue;
}
}
/* If the last character was a letter, we're in a symbol already */
if (isletter(c))
{
c = d;
continue;
}
/* If the current character is a letter, test for a symbol */
if (text.compare(i, sym.size(), sym) == 0)
return i;
c = d;
}
return -1;
}

36
compiler/scasm/amx_parser.h Executable file
View File

@ -0,0 +1,36 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#ifndef _INCLUDE_PARSER_H
#define _INCLUDE_PARSER_H
void StringBreak(std::string &Source, std::string &Left, std::string &Right);
int FindArguments(std::string &text, std::vector<std::string*> &List, int &end);
int FindSymbol(std::string &text, const std::string &sym, int startPos);
void ProcessDirective(std::string &text);
void StripComments(std::string &text);
void Strip(std::string &text);
char isletter(char c);
char literal(char c);
char expr(char c);
#endif //_INCLUDE_PARSER_H

101
compiler/scasm/amx_proc.cpp Executable file
View File

@ -0,0 +1,101 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#include "amxasm.h"
ProcMngr::~ProcMngr()
{
std::vector<ProcMngr::AsmProc *>::iterator i;
for (i=List.begin(); i!=List.end(); i++)
{
if ( (*i) )
delete (*i);
}
List.clear();
}
void ProcMngr::AddProc(SymbolList::Symbol *Symbol, Asm *ASM)
{
ProcMngr::AsmProc *a = new ProcMngr::AsmProc;
a->ASM = ASM;
a->Symbol = Symbol;
a->pb = false;
List.push_back(a);
}
bool ProcMngr::SetPublic(std::string &sym)
{
ProcMngr::AsmProc *a = NULL;
a = FindProc(sym);
if (a == NULL)
return false;
a->pb = true;
return true;
}
void ProcMngr::GetPublics(std::vector<ProcMngr::AsmProc *> &pbList)
{
std::vector<ProcMngr::AsmProc *>::iterator i;
for (i=List.begin(); i!=List.end(); i++)
{
if ((*i)->pb == true)
{
pbList.push_back( (*i) );
}
}
}
ProcMngr::AsmProc *ProcMngr::FindProc(std::string &sym)
{
std::vector<ProcMngr::AsmProc *>::iterator i;
for (i = List.begin(); i != List.end(); i++)
{
if ( (*i)->Symbol->IsEqual(sym) )
{
return (*i);
}
}
return NULL;
}
int ProcMngr::GetCip(std::string &sym)
{
ProcMngr::AsmProc *p = NULL;
p = FindProc(sym);
if (p == NULL)
return ncip;
return p->ASM->cip;
}

49
compiler/scasm/amx_proc.h Executable file
View File

@ -0,0 +1,49 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#ifndef _INCLUDE_AMXPROC_H
#define _INCLUDE_AMXPROC_H
class ProcMngr
{
public:
class AsmProc
{
public:
SymbolList::Symbol *Symbol;
Asm *ASM;
bool pb;
};
public:
~ProcMngr();
void AddProc(SymbolList::Symbol *Symbol, Asm *ASM);
ProcMngr::AsmProc *FindProc(std::string &sym);
int GetCip(std::string &sym);
bool SetPublic(std::string &sym);
void GetPublics(std::vector<ProcMngr::AsmProc *> &pbList);
private:
std::vector<ProcMngr::AsmProc *> List;
public:
static const int ncip = -1;
};
#endif //_INCLUDE_AMXPROC_H

105
compiler/scasm/amx_symbol.cpp Executable file
View File

@ -0,0 +1,105 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#include "amxasm.h"
bool is_valid_symbol_marker(char c)
{
if (c >= '0' && c <= '9')
return true;
if (isletter(c))
return true;
return false;
}
bool IsValidSymbol(std::string &text)
{
size_t i = 0;
if (!text.size() || !isletter(text[0]))
{
return false;
}
for (i=0; i<text.size(); i++)
{
if (!is_valid_symbol_marker(text[i]))
{
return false;
}
}
return true;
}
SymbolList::~SymbolList()
{
std::vector<SymbolList::Symbol *>::iterator i;
for (i=List.begin(); i!=List.end(); i++)
{
if ( (*i) )
delete (*i);
}
List.clear();
}
SymbolList::Symbol::Symbol(SymbolType t, const char *s, int l)
{
line = l;
sym.assign(s);
type = t;
}
int SymbolList::Symbol::IsEqual(std::string &s)
{
return (sym.compare(s)==0);
}
SymbolList::Symbol *SymbolList::AddSymbol(const char *s, SymbolType type, int line)
{
Symbol *sym = new Symbol(type, s, line);
List.push_back(sym);
return sym;
}
SymbolList::Symbol* SymbolList::FindSymbol(std::string &sym)
{
std::vector<Symbol*>::iterator i;
for (i=List.begin(); i!=List.end(); i++)
{
if ((*i)->IsEqual(sym))
return (*i);
}
return NULL;
}
void SymbolList::PrintTable()
{
std::vector<Symbol*>::iterator i;
for (i=List.begin(); i!=List.end(); i++)
{
printf("Symbol \"%s\" defined on line %d\n", (*i)->GetSymbol(), (*i)->GetLine());
}
}

67
compiler/scasm/amx_symbol.h Executable file
View File

@ -0,0 +1,67 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#ifndef _INCLUDE_SYMBOL_H
#define _INCLUDE_SYMBOL_H
bool IsValidSymbol(std::string &text);
typedef enum
{
Sym_None,
Sym_Define,
Sym_Macro,
Sym_Proc,
Sym_Dat,
Sym_Reserved,
Sym_Label,
Sym_Native,
} SymbolType;
class SymbolList
{
public:
class Symbol
{
public:
Symbol(SymbolType t, const char *s, int l);
const char *GetSymbol() { return sym.c_str(); }
SymbolType GetType() { return type; }
int GetLine() { return line; }
int IsEqual(std::string &s);
private:
SymbolType type;
std::string sym;
int line;
};
public:
~SymbolList();
SymbolList::Symbol* AddSymbol(const char *s, SymbolType type, int line);
SymbolList::Symbol* FindSymbol(std::string &sym);
void PrintTable();
private:
std::vector<Symbol*> List;
};
#endif //_INCLUDE_SYMBOL_H

71
compiler/scasm/amxasm.cpp Executable file
View File

@ -0,0 +1,71 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#include "amxasm.h"
std::string filename;
int main(int argc, char **argv)
{
printf("debug clamp.\n");
getchar();
get_options(argc, argv);
Compiler Program;
Program.Load(filename);
Program.Parse();
exit(0);
}
void get_options(int argc, char **argv)
{
int i = 0; /* index */
int opt_flag = 0; /* flag for option detection */
char *option = 0; /* option pointer */
for (i=1; i<argc; i++)
{
if (argv[i][0] == '-')
{
opt_flag = 1;
option = argv[i];
switch (argv[i][1])
{
case 'v':
{
opt_flag = 0; /* no options expected */
//print_version();
break;
} /* case */
} /* switch */
} else { /* - */
if (!opt_flag)
{
filename.assign(argv[i]);
} else {
/* TODO */
}
} /* if */
}
}

220
compiler/scasm/amxasm.h Executable file
View File

@ -0,0 +1,220 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#ifndef _INCLUDE_AMXASM_H
#define _INCLUDE_AMXASM_H
//C includes
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdarg.h>
#include <assert.h>
//C++ includes
#include <iostream>
#include <fstream>
#include <string>
#include <vector>
#include <stack>
#include <list>
#include <map>
class Asm
{
public:
int op;
std::vector<int> params;
int cip;
};
#include "amx.h"
#include "amx_error.h"
#include "cexpr.h"
#include "amx_parser.h"
#include "amx_symbol.h"
#include "amx_macro.h"
#include "amx_define.h"
#include "amx_data.h"
#include "amx_proc.h"
#include "amx_label.h"
#include "amx_natives.h"
#include "amx_compiler.h" //This should be last!
#define SMALL_CELL_SIZE 32
typedef enum
{
Asm_Invalid = -1,
Asm_None,
Asm_Data,
Asm_Code,
Asm_Public,
Asm_Native,
} AsmSection;
/* From amx.c */
typedef enum {
OP_NONE, /* invalid opcode */
OP_LOAD_PRI,
OP_LOAD_ALT,
OP_LOAD_S_PRI,
OP_LOAD_S_ALT,
OP_LREF_PRI,
OP_LREF_ALT,
OP_LREF_S_PRI,
OP_LREF_S_ALT,
OP_LOAD_I,
OP_LODB_I,
OP_CONST_PRI,
OP_CONST_ALT,
OP_ADDR_PRI,
OP_ADDR_ALT,
OP_STOR_PRI,
OP_STOR_ALT,
OP_STOR_S_PRI,
OP_STOR_S_ALT,
OP_SREF_PRI,
OP_SREF_ALT,
OP_SREF_S_PRI,
OP_SREF_S_ALT,
OP_STOR_I,
OP_STRB_I,
OP_LIDX,
OP_LIDX_B,
OP_IDXADDR,
OP_IDXADDR_B,
OP_ALIGN_PRI,
OP_ALIGN_ALT,
OP_LCTRL,
OP_SCTRL,
OP_MOVE_PRI,
OP_MOVE_ALT,
OP_XCHG,
OP_PUSH_PRI,
OP_PUSH_ALT,
OP_PUSH_R,
OP_PUSH_C,
OP_PUSH,
OP_PUSH_S,
OP_POP_PRI,
OP_POP_ALT,
OP_STACK,
OP_HEAP,
OP_PROC,
OP_RET,
OP_RETN,
OP_CALL,
OP_CALL_PRI,
OP_JUMP,
OP_JREL,
OP_JZER,
OP_JNZ,
OP_JEQ,
OP_JNEQ,
OP_JLESS,
OP_JLEQ,
OP_JGRTR,
OP_JGEQ,
OP_JSLESS,
OP_JSLEQ,
OP_JSGRTR,
OP_JSGEQ,
OP_SHL,
OP_SHR,
OP_SSHR,
OP_SHL_C_PRI,
OP_SHL_C_ALT,
OP_SHR_C_PRI,
OP_SHR_C_ALT,
OP_SMUL,
OP_SDIV,
OP_SDIV_ALT,
OP_UMUL,
OP_UDIV,
OP_UDIV_ALT,
OP_ADD,
OP_SUB,
OP_SUB_ALT,
OP_AND,
OP_OR,
OP_XOR,
OP_NOT,
OP_NEG,
OP_INVERT,
OP_ADD_C,
OP_SMUL_C,
OP_ZERO_PRI,
OP_ZERO_ALT,
OP_ZERO,
OP_ZERO_S,
OP_SIGN_PRI,
OP_SIGN_ALT,
OP_EQ,
OP_NEQ,
OP_LESS,
OP_LEQ,
OP_GRTR,
OP_GEQ,
OP_SLESS,
OP_SLEQ,
OP_SGRTR,
OP_SGEQ,
OP_EQ_C_PRI,
OP_EQ_C_ALT,
OP_INC_PRI,
OP_INC_ALT,
OP_INC,
OP_INC_S,
OP_INC_I,
OP_DEC_PRI,
OP_DEC_ALT,
OP_DEC,
OP_DEC_S,
OP_DEC_I,
OP_MOVS,
OP_CMPS,
OP_FILL,
OP_HALT,
OP_BOUNDS,
OP_SYSREQ_PRI,
OP_SYSREQ_C,
OP_FILE,
OP_LINE,
OP_SYMBOL,
OP_SRANGE,
OP_JUMP_PRI,
OP_SWITCH,
OP_CASETBL,
OP_SWAP_PRI,
OP_SWAP_ALT,
OP_PUSHADDR,
OP_NOP,
OP_SYSREQ_D,
OP_SYMTAG,
/* ----- */
OP_NUM_OPCODES
} OPCODE;
void get_options(int argc, char **argv);
void InitOpcodes();
#endif //_INCLUDE_AMXASM_H

6
compiler/scasm/asm_macro.h Executable file
View File

@ -0,0 +1,6 @@
#ifndef _INCLUDE_MACRO_H
#define _INCLUDE_MACRO_H
#endif //_INCLUDE_MACRO_H

199
compiler/scasm/assembler.vcproj Executable file
View File

@ -0,0 +1,199 @@
<?xml version="1.0" encoding="Windows-1252"?>
<VisualStudioProject
ProjectType="Visual C++"
Version="7.10"
Name="assembler"
ProjectGUID="{FFFC86BE-94E7-458A-A61B-4D0F3B45658B}"
Keyword="Win32Proj">
<Platforms>
<Platform
Name="Win32"/>
</Platforms>
<Configurations>
<Configuration
Name="Debug|Win32"
OutputDirectory="Debug"
IntermediateDirectory="Debug"
ConfigurationType="1"
CharacterSet="2">
<Tool
Name="VCCLCompilerTool"
Optimization="0"
PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
MinimalRebuild="TRUE"
BasicRuntimeChecks="3"
RuntimeLibrary="5"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
DebugInformationFormat="4"/>
<Tool
Name="VCCustomBuildTool"/>
<Tool
Name="VCLinkerTool"
OutputFile="$(OutDir)/assembler.exe"
LinkIncremental="2"
GenerateDebugInformation="TRUE"
ProgramDatabaseFile="$(OutDir)/assembler.pdb"
SubSystem="1"
TargetMachine="1"/>
<Tool
Name="VCMIDLTool"/>
<Tool
Name="VCPostBuildEventTool"/>
<Tool
Name="VCPreBuildEventTool"/>
<Tool
Name="VCPreLinkEventTool"/>
<Tool
Name="VCResourceCompilerTool"/>
<Tool
Name="VCWebServiceProxyGeneratorTool"/>
<Tool
Name="VCXMLDataGeneratorTool"/>
<Tool
Name="VCWebDeploymentTool"/>
<Tool
Name="VCManagedWrapperGeneratorTool"/>
<Tool
Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
</Configuration>
<Configuration
Name="Release|Win32"
OutputDirectory="Release"
IntermediateDirectory="Release"
ConfigurationType="1"
CharacterSet="2">
<Tool
Name="VCCLCompilerTool"
PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
RuntimeLibrary="4"
UsePrecompiledHeader="0"
WarningLevel="3"
Detect64BitPortabilityProblems="TRUE"
DebugInformationFormat="3"/>
<Tool
Name="VCCustomBuildTool"/>
<Tool
Name="VCLinkerTool"
OutputFile="$(OutDir)/assembler.exe"
LinkIncremental="1"
GenerateDebugInformation="TRUE"
SubSystem="1"
OptimizeReferences="2"
EnableCOMDATFolding="2"
TargetMachine="1"/>
<Tool
Name="VCMIDLTool"/>
<Tool
Name="VCPostBuildEventTool"/>
<Tool
Name="VCPreBuildEventTool"/>
<Tool
Name="VCPreLinkEventTool"/>
<Tool
Name="VCResourceCompilerTool"/>
<Tool
Name="VCWebServiceProxyGeneratorTool"/>
<Tool
Name="VCXMLDataGeneratorTool"/>
<Tool
Name="VCWebDeploymentTool"/>
<Tool
Name="VCManagedWrapperGeneratorTool"/>
<Tool
Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
</Configuration>
</Configurations>
<References>
</References>
<Files>
<Filter
Name="Source Files"
Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}">
<File
RelativePath=".\amx_compiler.cpp">
</File>
<File
RelativePath=".\amx_data.cpp">
</File>
<File
RelativePath=".\amx_define.cpp">
</File>
<File
RelativePath=".\amx_error.cpp">
</File>
<File
RelativePath=".\amx_label.cpp">
</File>
<File
RelativePath=".\amx_macro.cpp">
</File>
<File
RelativePath=".\amx_natives.cpp">
</File>
<File
RelativePath=".\amx_parser.cpp">
</File>
<File
RelativePath=".\amx_proc.cpp">
</File>
<File
RelativePath=".\amx_symbol.cpp">
</File>
<File
RelativePath=".\amxasm.cpp">
</File>
<File
RelativePath=".\cexpr.cpp">
</File>
</Filter>
<Filter
Name="Header Files"
Filter="h;hpp;hxx;hm;inl;inc;xsd"
UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}">
<File
RelativePath=".\amx.h">
</File>
<File
RelativePath=".\amx_compiler.h">
</File>
<File
RelativePath=".\amx_data.h">
</File>
<File
RelativePath=".\amx_define.h">
</File>
<File
RelativePath=".\amx_error.h">
</File>
<File
RelativePath=".\amx_label.h">
</File>
<File
RelativePath=".\amx_macro.h">
</File>
<File
RelativePath=".\amx_natives.h">
</File>
<File
RelativePath=".\amx_parser.h">
</File>
<File
RelativePath=".\amx_proc.h">
</File>
<File
RelativePath=".\amx_symbol.h">
</File>
<File
RelativePath=".\amxasm.h">
</File>
<File
RelativePath=".\cexpr.h">
</File>
</Filter>
</Files>
<Globals>
</Globals>
</VisualStudioProject>

284
compiler/scasm/cexpr.cpp Executable file
View File

@ -0,0 +1,284 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#include <string>
#include "amxasm.h"
CExpr::CExpr()
{
numVal = 0;
type = Val_None;
block = 0;
CError = NULL;
}
CExpr::CExpr(ErrorMngr *e)
{
numVal = 0;
type = Val_None;
block = 0;
CError = e;
}
CExpr::CExpr(ErrorMngr *e, std::string &text)
{
numVal = 0;
type = Val_None;
block = 0;
CError = e;
data.assign(text);
}
void CExpr::Clear()
{
if (type == Val_Block && block)
delete [] block;
numVal = 0;
type = Val_None;
block = 0;
}
CExpr::~CExpr()
{
if (block)
delete [] block;
}
char CExpr::IsLiteral(char c)
{
if (c == '"')
return '"';
if (c == '\'')
return '\'';
return 0;
}
char CExpr::IsHex(char c)
{
if (c >= '0' && c <= '9')
return c;
if (c >= 'A' && c <= 'F')
return c;
if (c >= 'a' && c <= 'f')
return c;
return 0;
}
cExprType CExpr::GetType()
{
return type;
}
void CExpr::Set(std::string &text)
{
data.assign(text);
}
int CExpr::DeHex(std::string blk)
{
size_t pos = 0, xc = 0, xpos = 0;
/* run through the characters */
for (pos = 0; pos < blk.size(); pos++)
{
if (blk[pos] == 'x')
{
xc++;
if (xc > 1)
break;
xpos = pos;
} else if (blk[pos] != ' '
&& (blk[pos] < '0' || blk[pos] > '9')
&& (!xc || (xc && !IsHex(blk[pos])))) {
CError->ErrorMsg(Err_Unexpected_Char, blk[pos]);
return 0;
}
}
if (xc > 1)
{
CError->ErrorMsg(Err_Unexpected_Char, 'x');
return 0;
}
if (xc)
{
if (xpos == 0 || blk[xpos-1] != '0')
{
if (CError)
CError->ErrorMsg(Warning_Hex_Start);
}
blk.erase(0, xpos+1);
pos = 0;
int j = 0;
while (blk[pos])
{
blk[pos] -= 48;
if (blk[pos] > 16)
blk[pos] -= 7;
if (blk[pos] >= 16)
blk[pos] -= 32;
if (blk[pos] >= 16 || blk[pos] < 0)
{
if (CError)
CError->ErrorMsg(Err_Unexpected_Char, blk[pos]);
return 0;
}
j *= 16;
j += blk[pos];
pos++;
}
return j;
}
return atoi(blk.c_str());
}
int CExpr::Size()
{
if (type == Val_String || type == Val_Block)
return numVal;
if (type == Val_Number)
return (SMALL_CELL_SIZE/8);
return 0;
}
const char *CExpr::GetString(int *d)
{
const char *ret = 0;
if (type == Val_String)
{
ret = data.c_str();
if (d != NULL)
*d = numVal;
} else if (type == Val_Block) {
ret = block;
if (d != NULL)
*d = numVal;
}
return ret;
}
int CExpr::GetNumber()
{
return numVal;
}
/* Returns true if the expr can be evaluated */
int CExpr::Analyze()
{
size_t pos = 0, xc = 0, xpos = 0;
/* run through the characters */
for (pos = 0; pos < data.size(); pos++)
{
if (data[pos] == 'x')
{
xc++;
if (xc > 1)
return 0;
xpos = pos;
} else if (data[pos] != ' '
&& (data[pos] < '0' || data[pos] > '9')
&& (!xc || (xc && !IsHex(data[pos])))) {
return 0;
}
}
return 1;
}
cExprType CExpr::Evaluate()
{
size_t i = 0, blk = 0;
char litc = 0, c = 0, csave = 0;
cExprType t = Val_None;
std::string num;
block = new char[2];
if (data.find('\'', 0) != std::string::npos || data.find('"', 0) != std::string::npos)
{
/* STRESS TEST */
for (i=0; i<data.size(); i++)
{
c = data[i];
if (IsLiteral(c) != 0)
{
if (litc == IsLiteral(c))
{
litc = 0;
/* The literal has terminated. Expect no more. */
if (i != data.size() - 1)
{
t = Val_Error;
if (CError)
CError->ErrorMsg(Err_String_Extra, data[i+1]);
} else {
/* STRING DISCOVERED */
t = Val_String;
numVal = (int)(data.size()+1);
break;
}
} else {
litc = IsLiteral(c);
}
}
}
} else if (data.find(' ', 0) != std::string::npos) {
/* Build a mem block from values, store length in numVal */
t = Val_Block;
size_t pos = 0, npos = 0;
numVal = 0;
pos = data.find(' ', 0);
block[numVal++] = DeHex(data.substr(0, pos));
while ((pos = data.find(' ', pos)) != std::string::npos)
{
npos = data.find(' ', pos+1);
block = (char *)realloc(block, numVal+2);
if (npos != std::string::npos)
{
block[numVal] = (char)DeHex(data.substr(pos, npos-pos));
} else {
block[numVal] = (char)DeHex(data.substr(pos));
}
pos++;
numVal++;
}
} else {
/* Just get the number */
t = Val_Number;
numVal = DeHex(data);
char buf[32];
sprintf(buf, "%d", numVal);
data.assign(buf);
}
if (litc)
{
if (CError)
CError->ErrorMsg(Err_String_Terminate);
}
type = t;
return t;
}

71
compiler/scasm/cexpr.h Executable file
View File

@ -0,0 +1,71 @@
/* AMX Assembler
* Copyright (C)2004 David "BAILOPAN" Anderson
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
* Version: $Id$
*/
#ifndef _INCLUDE_CEXPR_H
#define _INCLUDE_CEXPR_H
/* This class is used for a single expression element
* It reads in a symbol and evaluates it.
*/
typedef enum
{
Val_None,
Val_Error,
Val_String,
Val_String_Hex,
Val_String_Number,
Val_Number_Hex,
Val_Number,
Val_Block,
Val_Hex,
} cExprType;
class CExpr
{
public:
CExpr();
CExpr(ErrorMngr *e);
CExpr(ErrorMngr *e, std::string &text);
void Set(std::string &text);
const char *GetString(int *d=NULL);
int Analyze();
cExprType Evaluate();
cExprType GetType();
int GetNumber();
int Size();
void Clear();
~CExpr();
private:
char IsHex(char c);
char IsLiteral(char c);
int DeHex(std::string blk);
private:
char *block;
std::string data;
cExprType type;
int numVal;
private:
ErrorMngr *CError;
};
#endif //_INCLUDE_CEXPR_H