Overhauled Section checker, and added ability to find code in not executable segements.
This commit is contained in:
@@ -119,7 +119,7 @@ extraext: ${TOOLSOBJ}
|
|||||||
@CXX@ @CFLAGS@ -o ${TOOLSDIR}/extraext ${TOOLSDIR}/extraext.cpp ${TOOLSOBJ}
|
@CXX@ @CFLAGS@ -o ${TOOLSDIR}/extraext ${TOOLSDIR}/extraext.cpp ${TOOLSOBJ}
|
||||||
|
|
||||||
sec-test: ${TOOLSOBJ}
|
sec-test: ${TOOLSOBJ}
|
||||||
@CXX@ @CFLAGS@ -o ${TOOLSDIR}/sec-test ${TOOLSDIR}/sec-test.cpp ${TOOLSDIR}/fileutil.o
|
@CXX@ @CFLAGS@ -o ${TOOLSDIR}/sec-test ${TOOLSDIR}/sec-test.cpp ${TOOLSOBJ}
|
||||||
|
|
||||||
srccount: ${TOOLSOBJ}
|
srccount: ${TOOLSOBJ}
|
||||||
@CXX@ @CFLAGS@ -o ${TOOLSDIR}/srccount ${TOOLSDIR}/srccount.cpp ${TOOLSDIR}/fileutil.o
|
@CXX@ @CFLAGS@ -o ${TOOLSDIR}/srccount ${TOOLSDIR}/srccount.cpp ${TOOLSDIR}/fileutil.o
|
||||||
|
|||||||
@@ -21,44 +21,128 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
|||||||
This is part of a toolkit used to assist in ZSNES development
|
This is part of a toolkit used to assist in ZSNES development
|
||||||
|
|
||||||
This program tells us is a variable is declared in the wrong section.
|
This program tells us is a variable is declared in the wrong section.
|
||||||
|
Or if code is not in an executable section.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
#include <fstream>
|
#include <fstream>
|
||||||
|
#include "strutil.h"
|
||||||
using namespace std;
|
using namespace std;
|
||||||
|
|
||||||
#include "fileutil.h"
|
#include "fileutil.h"
|
||||||
|
|
||||||
#define LINE_LENGTH 500
|
#define LINE_LENGTH 500
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
bool contains_resx(const char *str)
|
||||||
|
{
|
||||||
|
return(!strncmp(str, "resd ", strlen("resd ")) ||
|
||||||
|
!strncmp(str, "resw ", strlen("resw ")) ||
|
||||||
|
!strncmp(str, "resb ", strlen("resb ")) ||
|
||||||
|
strstr(str, " resd ") ||
|
||||||
|
strstr(str, " resw ") ||
|
||||||
|
strstr(str, " resb ") ||
|
||||||
|
strstr(str, ",resd ") ||
|
||||||
|
strstr(str, ",resw ") ||
|
||||||
|
strstr(str, ",resb "));
|
||||||
|
}
|
||||||
|
|
||||||
|
bool contains_dx(const char *str)
|
||||||
|
{
|
||||||
|
return(!strncmp(str, "dd ", strlen("dd ")) ||
|
||||||
|
!strncmp(str, "dw ", strlen("dw ")) ||
|
||||||
|
!strncmp(str, "db ", strlen("db ")) ||
|
||||||
|
strstr(str, " dd ") ||
|
||||||
|
strstr(str, " dw ") ||
|
||||||
|
strstr(str, " db ") ||
|
||||||
|
strstr(str, ",dd ") ||
|
||||||
|
strstr(str, ",dw ") ||
|
||||||
|
strstr(str, ",db "));
|
||||||
|
}
|
||||||
|
|
||||||
|
bool label(const char *str)
|
||||||
|
{
|
||||||
|
return(!strchr(str, ' ') && !strchr(str, '\t') && (str[strlen(str)-1] == ':'));
|
||||||
|
}
|
||||||
|
|
||||||
void handle_file(const char *filename)
|
void handle_file(const char *filename)
|
||||||
{
|
{
|
||||||
enum sections { sec_unknown, sec_bss, sec_data, sec_text };
|
enum sections { sec_unknown, sec_bss, sec_data, sec_text, sec_macro };
|
||||||
|
|
||||||
ifstream file(filename, ios::in);
|
ifstream file(filename, ios::in);
|
||||||
if (file)
|
if (file)
|
||||||
{
|
{
|
||||||
char line[LINE_LENGTH];
|
char buffer[LINE_LENGTH];
|
||||||
sections cur_section = sec_unknown;
|
sections cur_section = sec_unknown, prev_section = sec_unknown;
|
||||||
for (size_t i = 0; file.getline(line, LINE_LENGTH); i++)
|
for (size_t i = 1; file.getline(buffer, LINE_LENGTH); i++)
|
||||||
{
|
{
|
||||||
if (!strcasecmp(line, "SECTION .BSS")) { cur_section = sec_bss; }
|
char *line = buffer;
|
||||||
if (!strcasecmp(line, "SECTION .DATA")) { cur_section = sec_data; }
|
|
||||||
if (!strcasecmp(line, "SECTION .text")) { cur_section = sec_text; }
|
|
||||||
|
|
||||||
if ((cur_section != sec_bss) &&
|
char *comment_p = strchr(line, ';');
|
||||||
(strstr(line, " resd ") || strstr(line, " resw ") || strstr(line, " resb ") ||
|
if (comment_p) { *comment_p = 0; }
|
||||||
(strstr(line, ",resd ") || strstr(line, ",resw ") || strstr(line, ",resb ")) ))
|
|
||||||
|
if (all_whitespace(line)) { continue; }
|
||||||
|
|
||||||
|
for (char *p = line+strlen(line)-1; isspace(*p); p--) { *p = 0; }
|
||||||
|
while (isspace(*line)) { line++; }
|
||||||
|
|
||||||
|
|
||||||
|
if (!strcasecmp(line, "SECTION .BSS"))
|
||||||
|
{
|
||||||
|
prev_section = cur_section;
|
||||||
|
cur_section = sec_bss;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!strcasecmp(line, "SECTION .DATA"))
|
||||||
|
{
|
||||||
|
prev_section = cur_section;
|
||||||
|
cur_section = sec_data;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!strcasecmp(line, "SECTION .text"))
|
||||||
|
{
|
||||||
|
prev_section = cur_section;
|
||||||
|
cur_section = sec_text;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!strncmp(line, "%macro", strlen("%macro")) ||
|
||||||
|
!strncmp(line, "%imacro", strlen("%imacro")))
|
||||||
|
{
|
||||||
|
prev_section = cur_section;
|
||||||
|
cur_section = sec_macro;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!strncmp(line, "%endmacro", strlen("%endmacro")))
|
||||||
|
{
|
||||||
|
cur_section = prev_section;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
if ((cur_section != sec_bss) && contains_resx(line))
|
||||||
{
|
{
|
||||||
cout << filename << ": line " << i << ": Error, resx in non BSS section. \"" << line << "\"" << endl;
|
cout << filename << ": line " << i << ": Error, resx in non BSS section. \"" << line << "\"" << endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((cur_section != sec_data) &&
|
if ((cur_section != sec_data) && contains_dx(line))
|
||||||
(strstr(line, " dd ") || strstr(line, " dw ") || strstr(line, " db ") ||
|
|
||||||
(strstr(line, ",dd ") || strstr(line, ",dw ") || strstr(line, ",db ")) ))
|
|
||||||
{
|
{
|
||||||
cout << filename << ": line " << i << ": Error, dx in non DATA section. \"" << line << "\"" << endl;
|
cout << filename << ": line " << i << ": Error, dx in non DATA section. \"" << line << "\"" << endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if ((cur_section != sec_text) && (cur_section != sec_macro))
|
||||||
|
{
|
||||||
|
if (!contains_resx(line) && !contains_dx(line) && !label(line) &&
|
||||||
|
!strstr(line, "NEWSYM") && !strstr(line, "EXTSYM") && !strstr(line, " equ ") &&
|
||||||
|
(*line != '%') && !strstr(line, "ALIGN") && strncmp(line, "bits ", strlen("bits ")))
|
||||||
|
{
|
||||||
|
cout << filename << ": line " << i << ": Error, code in non TEXT section. \"" << line << "\"" << endl;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
|||||||
@@ -44,3 +44,15 @@ void Tokenize(const string& str, vector<string>& tokens, const string& delimiter
|
|||||||
pos = str.find_first_of(delimiters, lastPos);
|
pos = str.find_first_of(delimiters, lastPos);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool all_whitespace(const char *str)
|
||||||
|
{
|
||||||
|
for (; *str; str++)
|
||||||
|
{
|
||||||
|
if (!isspace(*str))
|
||||||
|
{
|
||||||
|
return(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return(true);
|
||||||
|
}
|
||||||
|
|||||||
@@ -28,5 +28,6 @@ This is part of a toolkit used to assist in ZSNES development
|
|||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
void Tokenize(const std::string&, std::vector<std::string>&, const std::string&);
|
void Tokenize(const std::string&, std::vector<std::string>&, const std::string&);
|
||||||
|
bool all_whitespace(const char *);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
Reference in New Issue
Block a user