Add t2fasm
git-svn-id: svn://kolibrios.org@8142 a494cfbc-eb01-0410-851d-a64ba20cac60
This commit is contained in:
parent
eb45285dfe
commit
67673665fb
Binary file not shown.
4
programs/bcc32/t2fasm/Makefile
Executable file
4
programs/bcc32/t2fasm/Makefile
Executable file
@ -0,0 +1,4 @@
|
||||
t2fasm:
|
||||
g++ -c t2fasm.cpp
|
||||
g++ -o t2fasm t2fasm.o
|
||||
rm t2fasm.o
|
BIN
programs/bcc32/t2fasm/t2fasm
Executable file
BIN
programs/bcc32/t2fasm/t2fasm
Executable file
Binary file not shown.
420
programs/bcc32/t2fasm/t2fasm.cpp
Executable file
420
programs/bcc32/t2fasm/t2fasm.cpp
Executable file
@ -0,0 +1,420 @@
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <ctype.h>
|
||||
#include <cstring>
|
||||
#include <string>
|
||||
using namespace std;
|
||||
|
||||
char str[20000], *word[100];
|
||||
int wordlen[sizeof(word) / sizeof(word[0])];
|
||||
|
||||
char words_ignore[100][100] = { "?debug",
|
||||
"if",
|
||||
"ifdef",
|
||||
"ifndef",
|
||||
"endif",
|
||||
"macro",
|
||||
"endm",
|
||||
"dgroup",
|
||||
"assume",
|
||||
"segment",
|
||||
"ends",
|
||||
"public",
|
||||
"proc",
|
||||
"endp",
|
||||
"extrn",
|
||||
"model",
|
||||
"label",
|
||||
"end",
|
||||
""};
|
||||
|
||||
#define WI_macro (words_ignore[5])
|
||||
#define WI_endm (words_ignore[6])
|
||||
#define WI_segment (words_ignore[9])
|
||||
#define WI_ends (words_ignore[10])
|
||||
#define WI_proc (words_ignore[12])
|
||||
#define WI_endp (words_ignore[13])
|
||||
#define WI_label (words_ignore[16])
|
||||
const char *WI_END = "END";
|
||||
|
||||
int nwords_ignore = -1;
|
||||
char *words_ign_sort[sizeof(words_ignore) / sizeof(words_ignore[0])];
|
||||
|
||||
int strcmp1(const char *s0, int n0, const char *s1, int n1)
|
||||
{
|
||||
while (n0 && n1)
|
||||
{
|
||||
n0--; n1--;
|
||||
int c = (int)tolower(*s0) - (int)tolower(*s1);
|
||||
if (c < 0) return -1;
|
||||
if (c > 0) return 1;
|
||||
if (!*(s0++) || !*(s1++)) return 0;
|
||||
}
|
||||
if (n0 && *s0) return 1;
|
||||
if (n1 && *s1) return -1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int strlen1(const char *s, int n)
|
||||
{
|
||||
int i = 0;
|
||||
while (i < n && s[i]) i++;
|
||||
return i;
|
||||
}
|
||||
|
||||
char *strcpy1(char *r, const char *s, int n)
|
||||
{
|
||||
char *r0 = r;
|
||||
while (n-- && *s) *(r++) = *(s++);
|
||||
*r = 0;
|
||||
return r0;
|
||||
}
|
||||
|
||||
char *strchr1(char *s, int n, char c)
|
||||
{
|
||||
while (n-- && *s)
|
||||
{
|
||||
if (*s == c) return s;
|
||||
s++;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
char *first_not_space(char *s)
|
||||
{
|
||||
while (*s && isspace(*s)) s++;
|
||||
return s;
|
||||
}
|
||||
|
||||
char get_word(char *s)
|
||||
{
|
||||
int i = 0, k;
|
||||
for (k = 0; k < sizeof(word) / sizeof(word[0]); k++)
|
||||
{
|
||||
s = first_not_space(s + i);
|
||||
word[k] = s;
|
||||
i = 0;
|
||||
while (s[i] && !isspace(s[i]) && s[i] != ';' && s[i] != ',' && s[i] != ':')
|
||||
{
|
||||
i++;
|
||||
}
|
||||
if (i == 0)
|
||||
{
|
||||
if (s[i] != ',' && s[i] != ':') break;
|
||||
i = 1;
|
||||
}
|
||||
wordlen[k] = i;
|
||||
}
|
||||
for (; k < sizeof(word) / sizeof(word[0]); k++)
|
||||
{
|
||||
word[k] = s; wordlen[k] = 0;
|
||||
}
|
||||
return s[i];
|
||||
}
|
||||
|
||||
void build_words_ignore()
|
||||
{
|
||||
int i, j;
|
||||
nwords_ignore = 0;
|
||||
while (words_ignore[nwords_ignore][0])
|
||||
{
|
||||
words_ign_sort[nwords_ignore] = words_ignore[nwords_ignore];
|
||||
nwords_ignore++;
|
||||
}
|
||||
for (i = 0; i < nwords_ignore; i++) for (j = 0; j < i; j++)
|
||||
{
|
||||
if (strcmp1(words_ign_sort[j], -1, words_ign_sort[i], -1) > 0)
|
||||
{
|
||||
char *s = words_ign_sort[j];
|
||||
words_ign_sort[j] = words_ign_sort[i];
|
||||
words_ign_sort[i] = s;
|
||||
}
|
||||
}
|
||||
words_ign_sort[nwords_ignore] = words_ignore[nwords_ignore];
|
||||
}
|
||||
|
||||
int find_word_ign_sort(const char *s, int n)
|
||||
{
|
||||
int i0, i1, i;
|
||||
if (nwords_ignore < 0) build_words_ignore();
|
||||
i0 = -1; i1 = nwords_ignore;
|
||||
while (i1 > i0 + 1)
|
||||
{
|
||||
i = (i0 + i1) / 2;
|
||||
if (strcmp1(s, n, words_ign_sort[i], -1) > 0) i0 = i;
|
||||
else i1 = i;
|
||||
}
|
||||
return i1;
|
||||
}
|
||||
|
||||
char *find_word_ignore(const char *s, int n)
|
||||
{
|
||||
int i = find_word_ign_sort(s, n);
|
||||
return (strcmp1(s, n, words_ign_sort[i], -1) == 0) ? words_ign_sort[i] : 0;
|
||||
}
|
||||
|
||||
char *add_word_ignore(const char *s, int n)
|
||||
{
|
||||
int i = find_word_ign_sort(s, n), j;
|
||||
if (strcmp1(s, n, words_ign_sort[i], -1) != 0)
|
||||
{
|
||||
if (s[0] && strlen1(s, n) < sizeof(words_ignore[0]) &&
|
||||
words_ignore[nwords_ignore+1] < words_ignore[0] + sizeof(words_ignore))
|
||||
{
|
||||
strcpy1(words_ignore[nwords_ignore], s, n);
|
||||
words_ignore[nwords_ignore+1][0] = 0;
|
||||
for (j = nwords_ignore; j >= i; j--) words_ign_sort[j+1] = words_ign_sort[j];
|
||||
words_ign_sort[i] = words_ignore[nwords_ignore];
|
||||
nwords_ignore++;
|
||||
words_ign_sort[nwords_ignore] = words_ignore[nwords_ignore];
|
||||
}
|
||||
else return 0;
|
||||
}
|
||||
return words_ign_sort[i];
|
||||
}
|
||||
|
||||
struct CSegment
|
||||
{
|
||||
char name[100];
|
||||
int state;
|
||||
string text;
|
||||
};
|
||||
|
||||
int nsegment = 0, cursegment = 0, stack_segment[50], nstack_segment = 0;
|
||||
CSegment segment[100];
|
||||
|
||||
void push_stack_segment()
|
||||
{
|
||||
if (nstack_segment < sizeof(stack_segment) / sizeof(stack_segment[0]))
|
||||
{
|
||||
stack_segment[nstack_segment] = cursegment;
|
||||
}
|
||||
nstack_segment++;
|
||||
}
|
||||
|
||||
void pop_stack_segment()
|
||||
{
|
||||
if (nstack_segment > 0) nstack_segment--;
|
||||
if (nstack_segment < sizeof(stack_segment) / sizeof(stack_segment[0]))
|
||||
{
|
||||
cursegment = stack_segment[nstack_segment];
|
||||
}
|
||||
}
|
||||
|
||||
void newsegment()
|
||||
{
|
||||
segment[nsegment].name[0] = 0;
|
||||
segment[nsegment].state = 0;
|
||||
segment[nsegment].text = "";
|
||||
cursegment = nsegment++;
|
||||
}
|
||||
|
||||
void tosegment(char *name, int nameL)
|
||||
{
|
||||
int i;
|
||||
cursegment = 0;
|
||||
if (strlen1(name, nameL) >= sizeof(segment[0].name)) return;
|
||||
for (i = 0; i < nsegment; i++)
|
||||
{
|
||||
if (strcmp1(name, nameL, segment[i].name, -1) == 0)
|
||||
{
|
||||
cursegment = i;
|
||||
return;
|
||||
}
|
||||
}
|
||||
if (nsegment >= sizeof(segment) / sizeof(segment[0])) return;
|
||||
newsegment();
|
||||
strcpy1(segment[cursegment].name, name, nameL);
|
||||
}
|
||||
|
||||
void outsegment()
|
||||
{
|
||||
if (segment[cursegment].state == 0) return;
|
||||
fputs("\nsegment", stdout);
|
||||
if (segment[cursegment].name[0])
|
||||
{
|
||||
fputc(' ', stdout);
|
||||
fputs(segment[cursegment].name, stdout);
|
||||
}
|
||||
fputc('\n', stdout);
|
||||
fputs(segment[cursegment].text.c_str(), stdout);
|
||||
fputs("endseg", stdout);
|
||||
if (segment[cursegment].name[0])
|
||||
{
|
||||
fputs(" ", stdout);
|
||||
fputs(segment[cursegment].name, stdout);
|
||||
}
|
||||
fputc('\n', stdout);
|
||||
}
|
||||
|
||||
void transform_label(int in_define, bool label = false)
|
||||
{
|
||||
if (in_define)
|
||||
{
|
||||
memmove(str + 8, word[0], wordlen[0]);
|
||||
memcpy(str, "nextdef ", 8);
|
||||
str[wordlen[0]+8] = '\n';
|
||||
str[wordlen[0]+9] = 0;
|
||||
}
|
||||
else if (label)
|
||||
{
|
||||
memmove(str, word[0], wordlen[0]);
|
||||
str[wordlen[0]] = ':';
|
||||
str[wordlen[0]+1] = '\n';
|
||||
str[wordlen[0]+2] = 0;
|
||||
}
|
||||
segment[cursegment].state |= 4;
|
||||
}
|
||||
|
||||
int main()
|
||||
{
|
||||
char *s;
|
||||
int in_macro = 0, in_define = 0, i;
|
||||
newsegment();
|
||||
for (;;)
|
||||
{
|
||||
i = sizeof(str) - 200;
|
||||
if (!fgets(str, i, stdin)) break;
|
||||
if ((s = strchr(str, '\n')) == NULL)
|
||||
{
|
||||
if (strlen(str) < i-1) strcat(str, "\n");
|
||||
else
|
||||
{
|
||||
while (fgets(str, sizeof(str), stdin))
|
||||
{
|
||||
if (strchr(str, '\n')) break;
|
||||
}
|
||||
continue;
|
||||
}
|
||||
}
|
||||
char* p;
|
||||
while (p=strstr(str,"st("))
|
||||
{
|
||||
p[2]=p[3];
|
||||
memmove(p+3,p+5,strlen(p+5)+1);
|
||||
}
|
||||
get_word(str);
|
||||
if (word[1][0] == ':') transform_label(in_define, false);
|
||||
else
|
||||
{
|
||||
if (word[0][0] == '.') continue;
|
||||
if (strcmp1(word[0], wordlen[0], WI_macro, -1) == 0 ||
|
||||
strcmp1(word[1], wordlen[1], WI_macro, -1) == 0)
|
||||
{
|
||||
add_word_ignore(word[0], wordlen[0]);
|
||||
in_macro++;
|
||||
continue;
|
||||
}
|
||||
if (strcmp1(word[0], wordlen[0], WI_endm, -1) == 0)
|
||||
{
|
||||
if (in_macro > 0) in_macro--;
|
||||
continue;
|
||||
}
|
||||
if (strcmp1(word[1], wordlen[1], WI_segment, -1) == 0)
|
||||
{
|
||||
push_stack_segment();
|
||||
add_word_ignore(word[0], wordlen[0]);
|
||||
tosegment(word[0], wordlen[0]);
|
||||
continue;
|
||||
}
|
||||
if (strcmp1(word[1], wordlen[1], WI_ends, -1) == 0)
|
||||
{
|
||||
pop_stack_segment();
|
||||
continue;
|
||||
}
|
||||
if (find_word_ignore(word[0], wordlen[0])) continue;
|
||||
if (wordlen[0] == 0 || strcmp1(word[0], wordlen[0], "align", -1) == 0)
|
||||
{
|
||||
if (word[0][0] == 0) {str[0] = '\n'; str[1] = 0;}
|
||||
}
|
||||
else if (strcmp1(word[1], wordlen[1], WI_endp, -1) == 0)
|
||||
{
|
||||
if (in_define > 0) strcpy(str, (--in_define) ? "newdef\n" : "enddef\n");
|
||||
}
|
||||
else if (strcmp1(word[1], wordlen[1], WI_proc, -1) == 0)
|
||||
{
|
||||
memmove(str + 8, word[0], wordlen[0]);
|
||||
memcpy(str, (in_define++) ? "newdef " : "define ", 8);
|
||||
str[wordlen[0]+8] = '\n';
|
||||
str[wordlen[0]+9] = 0;
|
||||
segment[cursegment].state |= 4;
|
||||
}
|
||||
else if (strcmp1(word[1], wordlen[1], WI_label, -1) == 0)
|
||||
{
|
||||
transform_label(in_define, true);
|
||||
}
|
||||
else
|
||||
{
|
||||
for (i = 0; i <= 1; i++)
|
||||
{
|
||||
if (strcmp1(word[i], wordlen[i], "db", -1) == 0 &&
|
||||
wordlen[i+2] >= 3 && strcmp1(word[i+2], 3, "dup", 3) == 0)
|
||||
{
|
||||
if (word[i][0] == 'd') word[i][0] = 'r';
|
||||
else if (word[i][0] == 'D') word[i][0] = 'R';
|
||||
word[i+1][wordlen[i+1]] = '\n';
|
||||
word[i+1][wordlen[i+1]+1] = 0;
|
||||
segment[cursegment].state |= 2;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (i > 1)
|
||||
{
|
||||
int word_shift = 0;
|
||||
for (i = 1; i < sizeof(word) / sizeof(word[0]); i++)
|
||||
{
|
||||
word[i] += word_shift;
|
||||
if (wordlen[i] >= 4 && word[i][0] != '[' &&
|
||||
word[i][wordlen[i]-1] == ']' &&
|
||||
(s = strchr1(word[i], wordlen[i], '[')) != 0)
|
||||
{
|
||||
*s = '+';
|
||||
memmove(word[i] + 1, word[i], strlen(word[i]) + 1);
|
||||
word[i][0] = '[';
|
||||
wordlen[i]++;
|
||||
word_shift++;
|
||||
}
|
||||
else if (wordlen[i] >= 1 && !strchr1(word[i], wordlen[i], '[') &&
|
||||
strcmp1(word[i-1], wordlen[i-1], "ptr", -1) == 0)
|
||||
{
|
||||
memmove(word[i] + wordlen[i] + 2, word[i] + wordlen[i],
|
||||
strlen(word[i] + wordlen[i]) + 1);
|
||||
memmove(word[i] + 1, word[i], wordlen[i]);
|
||||
word[i][0] = '['; word[i][wordlen[i] + 1] = ']';
|
||||
wordlen[i] += 2;
|
||||
word_shift += 2;
|
||||
}
|
||||
else if (wordlen[i] >= 5 && word[i][wordlen[i]-1] == ')' &&
|
||||
strcmp1(word[i], wordlen[i], "st(", -1))
|
||||
{
|
||||
memmove(word[i] + 2, word[i] + 3, wordlen[i] - 4);
|
||||
memmove(word[i] + wordlen[i] - 2, word[i] + wordlen[i],
|
||||
strlen(word[i] + wordlen[i]) + 1);
|
||||
word_shift -= 2;
|
||||
}
|
||||
}
|
||||
segment[cursegment].state |= 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (in_macro) continue;
|
||||
if ((s = strchr(str, ';')) != NULL)
|
||||
{
|
||||
s[0] = '\n'; s[1] = 0;
|
||||
if (!first_not_space(str)[0]) continue;
|
||||
}
|
||||
segment[cursegment].text += str;
|
||||
}
|
||||
for (cursegment = 0; cursegment < nsegment; cursegment++)
|
||||
{
|
||||
if ((segment[cursegment].state & 3) != 2) outsegment();
|
||||
}
|
||||
fputs("\nI_END:\n", stdout);
|
||||
for (cursegment = 0; cursegment < nsegment; cursegment++)
|
||||
{
|
||||
if ((segment[cursegment].state & 3) == 2) outsegment();
|
||||
}
|
||||
fputs("\nalign 0x10\nU_END:\n", stdout);
|
||||
return 0;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user