#if (!defined(NTSYS__S_ASSEMBLER_H___)) #define NTSYS__S_ASSEMBLER_H___ #define ntsys_exit_if_error(parser) if (!ntsys_asm_arg_new((parser)->string, (parser)->cache)) #define ntsys_run_asm_parser(ss) __ntsys_arg_function_loader(&(ss)) #define create_ntsys_asm_parser(cache, fp, str, table, table_size, labels, labels_pos, labels_count, cyc, f_sz) ((ntsys_argument_parser_t){(cache), (fp), (str), (table), (table_size), (labels), (labels_pos), (labels_count), (cyc), (f_sz), NULL}) #define create_ntsys_asm_save(ss) ((ntsys_asm_save_t){(ss), (ss)}) #define create_ntsys_asm_cache(ss) ((ntsys_asm_cache_t)&(ss)) #define ntsys_asm_arg_new(str, __cache) ((ntsys_get_arg((__cache))) && ((str) = __cache->string)) #define ntsys_asm_arg_or_zero_len_str(str, __cache) ((((ntsys_get_arg((__cache))) && ((str) = __cache->string)) == NULL) ? ("") : (str)) /* * #define __SPACE_SHIFT while (is_space(st[pos])) { pos ++; } * #define __NEXT_ARG {__e_byte_t isStr = 0;while (!is_space(st[save]) || isStr == 1) { if (st[save] == '"' && st[save - 1] != '\\') {isStr = !isStr;}save ++; }}while (is_space(st[save])) { save ++; }{size_t n_p = save;__e_byte_t isStr = 0;while (!is_space(st[n_p]) || isStr == 1) { if (st[n_p] == '"' && st[n_p - 1] != '\\') {isStr = !isStr;}n_p ++; }st[n_p] = '\0';} * #define get_mem_pos() *mem_pos = ftell(fp) == 0 ? 0 : ftell(fp) - 1; */ #define __READ_FILE_WITH_EOF_OR_LN ((c = getc(fp)) != EOF && c != '\n' && c != '\r') #define is_space(c) (c >= 0 && c <= 32) char* ntsys_get_str(char* ptr, FILE* fp) { if (ptr != NULL) { free(ptr); } unsigned long len = 0; int c; { unsigned long save_ptr = ftell(fp); while (__READ_FILE_WITH_EOF_OR_LN) { len ++; } fseek(fp, save_ptr, SEEK_SET); } if (len == 0) return NULL; ptr = malloc(len + 1); if (ptr == NULL) { ntsys_error("Out of memory!"); return NULL; } len = 0; while (__READ_FILE_WITH_EOF_OR_LN) { ptr[len] = c; len ++; } ptr[len] = '\0'; size_t i = 0; __e_byte_t isStr = 0; while (i < strlen(ptr)) { if (ptr[i] == '"' && ptr[((i == 0) ? 1 : i) - 1] != '\\') {isStr = !isStr;} if ((ptr[i] == ';' || ptr[i] == '#') && isStr == 0) ptr[i] = '\0'; if ((ptr[i] == ',') && isStr == 0) ptr[i] = ' '; i ++; } return ptr; } #undef __READ_FILE_WITH_EOF_OR_LN typedef struct { char* string; char* cache; } ntsys_asm_save_t; typedef ntsys_asm_save_t* ntsys_asm_cache_t; static void __str_slice(char* str) { size_t i = 1; while (i < strlen(str)) { str[i - 1] = str[i]; i ++; } str[strlen(str) - 1] = '\0'; } char* ntsys_get_arg(ntsys_asm_cache_t save) { char* str = save->cache; printf("Cache : %s\n", save->cache); while (1) { if ((!is_space(str[0])) || str[0] == '\0') { break; } str ++; } { size_t n_p = 0; __e_byte_t isStr = 0; while (1) { if (str[n_p] == '"' && str[((n_p == 0) ? 1 : n_p) - 1] != '\\') {isStr = !isStr;} if ((is_space(str[n_p]) && isStr == 0) || str[n_p] == '\0') { break; } n_p ++; } byte_t t = 1; if (n_p + t > strlen(str)) t = 0; save->cache = &str[n_p + t]; str[n_p] = '\0'; } printf("Switch : %s\n", save->cache); if (str[strlen(str) - 1] == '\n' || str[strlen(str) - 1] == '\r') str[strlen(str) - 1] = '\0'; if (strlen(str) == 0) { str = NULL; save->string = NULL; return NULL; } if (str[0] == '"') { str ++; if (str[strlen(str) - 1] != '"' || str[(strlen(str) < 2 ? 2 : strlen(str)) - 2] == '\\') { ntsys_error("No close of string!"); str = NULL; save->string = NULL; return NULL; } else { str[strlen(str) - 1] = '\0'; size_t i = 0; while (i < strlen(str)) { if (str[i] == '\\') { __str_slice(&str[i]); switch (str[i]) { case '0': str[i] = '\0'; break; case 'a': str[i] = '\a'; break; case 'b': str[i] = '\b'; break; case 't': str[i] = '\t'; break; case 'n': str[i] = '\n'; break; case 'v': str[i] = '\v'; break; case 'f': str[i] = '\f'; break; case 'r': str[i] = '\r'; break; default: ntsys_error("Unknown ident!"); str = NULL; save->string = NULL; return NULL; break; } } i ++; } } } save->string = str; printf("Loading : %s\n", save->string); return str; } typedef char** ntsys_labels_array_t; typedef struct { ntsys_asm_cache_t cache; FILE* fp; char* string; char** table; size_t table_length; char** labels; word_t* labels_positions; size_t* labels_count; byte_t is_rewrite; dword_t* file_size; word_t* memory_size; } ntsys_argument_parser_t; static void __input_datatype(ntsys_argument_parser_t* parser, byte_t* mode) { ntsys_exit_if_error(parser) { ntsys_error("Cannot find argument!"); return; } byte_t data_type = 0x01; char* str = parser->string; if (strcmp(str, "byte") == 0) { data_type = 0x01; } else if (strcmp(str, "word") == 0) { data_type = 0x02; } else if (strcmp(str, "dword") == 0) { data_type = 0x04; } else if (strcmp(str, "qword") == 0) { data_type = 0x08; } else if (strcmp(str, "sbyte") == 0) { data_type = 0xF1; } else if (strcmp(str, "sword") == 0) { data_type = 0xF2; } else if (strcmp(str, "sdword") == 0) { data_type = 0xF4; } else if (strcmp(str, "sqword") == 0) { data_type = 0xF8; } else if (strcmp(str, "db") == 0) { data_type = 0xB2; } else { ntsys_error("Incorrect datatype!"); return; } if (data_type == 0xB2) fputc((__e_byte_t)0x02, parser->fp); else fputc((__e_byte_t)data_type, parser->fp); *mode = data_type; } static void __write_label(ntsys_argument_parser_t* parser) { if (parser->is_rewrite == 0) { putc('E', parser->fp); putc('F', parser->fp); return; } size_t i = 0; /* printf("Count: 0x%04lX\n", *(parser->labels_count)); */ while (i < *(parser->labels_count)) { /* printf("Label: \"%s\" to \"%s\"\n", parser->string, parser->labels[i]); */ if (strcmp(parser->string, parser->labels[i]) == 0) { word_t cnt = parser->labels_positions[i]; int __i = 1; if (!(*((char *)&__i) == 1)) { /* BIG ENDIAN */ byte_t* ar = (byte_t*)&cnt; byte_t s = ar[0]; ar[0] = ar[1]; ar[1] = s; } fwrite(&cnt, 1, sizeof(word_t), parser->fp); return; } i ++; } } static void __input_data(ntsys_argument_parser_t* parser, byte_t* mode) { ntsys_exit_if_error(parser) { ntsys_error("Cannot find argument!"); return; } byte_t data_type = *mode; char* str = parser->string; if (str[0] >= '0' && str[0] <= '9') { int count_system = 10; if (str[1] == 'x') { count_system = 16; } else if (str[1] == 'b') { count_system = 2; } else { ntsys_error("Unknown number system!"); return; } if (count_system != 10) { str += 2; } long cnt = strtol(str, NULL, count_system); FILE* fp = parser->fp; int __i = 1; if (!(*((char *)&__i) == 1)) { /* BIG ENDIAN */ if ((data_type & 0x0F) != 0x01) { size_t i = 0; byte_t* ar = (byte_t*)&cnt; while (i < (data_type & 0x0F)) { byte_t s = ar[i]; ar[i] = ar[(data_type & 0x0F) - i - 1]; ar[(data_type & 0x0F) - i - 1] = s; i ++; } } } switch (data_type) { case 0x01: fwrite((__e_byte_t*)((byte_t*)&cnt), 1, sizeof(byte_t), fp); break; case 0x02: fwrite((__e_byte_t*)((word_t*)&cnt), 1, sizeof(word_t), fp); break; case 0x04: fwrite((__e_byte_t*)((dword_t*)&cnt), 1, sizeof(dword_t), fp); break; case 0x08: fwrite((__e_byte_t*)((qword_t*)&cnt), 1, sizeof(qword_t), fp); break; case 0xF1: fwrite((__e_byte_t*)((sbyte_t*)&cnt), 1, sizeof(sbyte_t), fp); break; case 0xF2: fwrite((__e_byte_t*)((sword_t*)&cnt), 1, sizeof(sword_t), fp); break; case 0xF4: fwrite((__e_byte_t*)((sdword_t*)&cnt), 1, sizeof(sdword_t), fp); break; case 0xF8: fwrite((__e_byte_t*)((sqword_t*)&cnt), 1, sizeof(sqword_t), fp); break; } } else { if (data_type != 0xB2) { ntsys_error("Incorrect datatype! For jump to label please use db type!"); return; } __write_label(parser); } } static void __input_string(ntsys_argument_parser_t* parser) { ntsys_exit_if_error(parser) { ntsys_error("Cannot find argument!"); return; } char* str = parser->string; size_t i = 0; while (i < strlen(str)) { fputc(str[i], parser->fp); i ++; } fputc('\0', parser->fp); } static int __arg_writer(char* str, ntsys_argument_parser_t* parser, byte_t* mode) { if (str[0] == ':') { if (str[1] == 'T') { __input_datatype(parser, mode); } else if (str[1] == 'D') { __input_data(parser, mode); } else if (str[1] == 'S') { __input_string(parser); } } else { byte_t x = strtol(str, NULL, 16); fputc((char)x, parser->fp); /* printf("Input: 0x%04X\n", x); */ } return EXIT_SUCCESS; } int __load_label(ntsys_argument_parser_t* parser) { char* str = parser->string; str[strlen(str) - 1] = '\0'; parser->labels[*(parser->labels_count)] = malloc(strlen(str) + 1); if (parser->labels[*(parser->labels_count)] == NULL) { ntsys_error("Out of memory!"); return EXIT_FAILURE; } strcpy(parser->labels[*(parser->labels_count)], str); parser->labels_positions[*(parser->labels_count)] = (word_t)(ftell(parser->fp)); /* printf("Label: \"%s\" on 0x%08X\n", str, parser->labels_positions[*(parser->labels_count)]); */ *parser->labels_count += 1; return EXIT_SUCCESS; } static int select_argument(ntsys_argument_parser_t* parser) { size_t i = 0; byte_t internal = 0x00; char* str = parser->string; if (str[strlen(str) - 1] == ':' && parser->is_rewrite == 0) { return __load_label(parser); } if (str[strlen(str) - 1] == ':') return EXIT_SUCCESS; char buf[64]; char** table = parser->table; while (i < parser->table_length) { size_t t = 0; while (t < strlen(table[i])) { if (table[i][t] == '=') break; t ++; } strncpy(buf, table[i], t); buf[t] = '\0'; if (strcmp(str, buf) == 0) { char* se = &table[i][t + 1]; while (strlen(se) > 1) { char is[3]; strncpy(is, se, 2); is[2] = '\0'; if (__arg_writer(is, parser, &internal) == EXIT_FAILURE) { ntsys_error("Internal program error!"); return EXIT_FAILURE; } se += sizeof(char) * 2; } return EXIT_SUCCESS; } i ++; } printf("\033[1mntsys: \033[91mUndefined operator \"%s\"!\033[0m\n", str); return EXIT_FAILURE; } byte_t fGH6VSEzu7qNiGVE_hd_ew = 0; static void __write_header(ntsys_argument_parser_t* parser) { if (fGH6VSEzu7qNiGVE_hd_ew == 1) return; fGH6VSEzu7qNiGVE_hd_ew = 1; fputc(0x4D, parser->fp); fputc(0x5A, parser->fp); parser->memory_size = &fGH6VSEzu7qNiGVE_mem_size; *parser->file_size += 8; int __i = 1; if (!(*((char *)&__i) == 1)) { /* BIG ENDIAN */ size_t i = 0; byte_t* ar = (byte_t*)parser->file_size; while (i < (sizeof(dword_t))) { byte_t s = ar[i]; ar[i] = ar[(sizeof(dword_t)) - i - 1]; ar[(sizeof(dword_t)) - i - 1] = s; i ++; } ar = (byte_t*)parser->memory_size; byte_t s = ar[0]; ar[0] = ar[1]; ar[1] = s; } fwrite(parser->file_size, 1, sizeof(dword_t), parser->fp); fwrite(parser->memory_size, 1, sizeof(word_t), parser->fp); } int __ntsys_arg_function_loader(ntsys_argument_parser_t* parser) { if (parser->is_rewrite) __write_header(parser); while (ntsys_asm_arg_new(parser->string, parser->cache)) { if (select_argument(parser) == EXIT_FAILURE) return EXIT_FAILURE; } if (parser->is_rewrite == 0) *parser->file_size = ftell(parser->fp) + 1; return EXIT_SUCCESS; } #undef is_space #endif