#undef	NDEBUG
#include "asn1fix_internal.h"

#ifdef	WIN32
#include <io.h>
#include <direct.h>
#define	chdir _chdir
#else
#include <dirent.h>
#include <sysexits.h>
#endif
#include <errno.h>

#include "asn1fix.h"

static int check(const char *fname,
	enum asn1p_flags parser_flags,
	enum asn1f_flags fixer_flags);
static int post_fix_check(asn1p_t *asn);
static int post_fix_check_element(asn1p_module_t *mod, asn1p_expr_t *expr);

int
main(int ac, char **av) {
#ifdef	WIN32
	intptr_t dir;
	struct _finddata_t c_file;
#else
	struct dirent *dp;
	DIR *dir;
#endif
	int failed = 0;
	int completed = 0;
	enum asn1p_flags parser_flags = A1P_NOFLAGS;
	enum asn1f_flags fixer_flags  = A1F_NOFLAGS;
	const char *filename;
	size_t len;
	int ret;

	/*
	 * Just in case when one decides that some flags better be
	 * enabled during `ASN1_FIXER_FLAGS=1 make check` or some
	 * similar usage.
	 */
	if(getenv("ASN1_PARSER_FLAGS"))
		parser_flags = atoi(getenv("ASN1_PARSER_FLAGS"));
	if(getenv("ASN1_FIXER_FLAGS"))
		fixer_flags = atoi(getenv("ASN1_FIXER_FLAGS"));

	/*
	 * Go into a directory with tests.
	 */
	if(ac <= 1) {
		fprintf(stderr, "Testing in ./tests...\n");
		ret = chdir("../tests");
		assert(ret == 0);
#ifdef	WIN32
		dir = _findfirst("*.asn1", &c_file);
		assert(dir != -1L);
#else
		dir = opendir(".");
		assert(dir);
#endif	/* WIN32 */
	} else {
		dir = 0;
	}

	/*
	 * Scan every *.asn1 file and try to parse and fix it.
	 */
	if(dir) {
#ifdef	WIN32
		do {
			filename = c_file.name;
#else
		while((dp = readdir(dir))) {
			filename = dp->d_name;
#endif	/* WIN32 */
			len = strlen(filename);
			if(len && strcmp(filename + len - 5, ".asn1") == 0) {
				ret = check(filename, parser_flags,fixer_flags);
				if(ret) {
					fprintf(stderr, "FAILED: %s\n",
						filename);
					failed++;
				}
				completed++;
			}
#ifdef	WIN32
		} while(_findnext(dir, &c_file) == 0);
		_findclose(dir);
#else
		}
		closedir(dir);
#endif	/* WIN32 */


		fprintf(stderr,
			"Tests COMPLETED: %d\n"
			"Tests FAILED:    %d\n"
			,
			completed, failed
		);
	} else {
		int i;
		for(i = 1; i < ac; i++) {
			ret = check(av[i], parser_flags, fixer_flags);
			if(ret) {
				fprintf(stderr, "FAILED: %s\n", av[i]);
				failed++;
			}
			completed++;
		}
	}

	if(completed == 0) {
		fprintf(stderr, "No tests defined?!\n");
		exit(EX_NOINPUT);
	}

	if(failed)
		exit(EX_DATAERR);
	return 0;
}

static int
check(const char *fname,
		enum asn1p_flags parser_flags,
		enum asn1f_flags fixer_flags) {
	asn1p_t *asn;
	int expected_parseable;		/* Is it expected to be parseable? */
	int expected_fix_code;		/* What code a fixer must return */
	int r_value = 0;

	/*
	 * Figure out how the processing should go by inferring
	 * expectations from the file name.
	 */
	if(strstr(fname, "-OK.")) {
		expected_parseable = 1;
		expected_fix_code  = 0;
	} else if(strstr(fname, "-NP.")) {
		expected_parseable = 0;
		expected_fix_code  = 123;	/* Does not matter */
	} else if(strstr(fname, "-SE.")) {
		expected_parseable = 1;
		expected_fix_code  = -1;	/* Semantically incorrect */
	} else if(strstr(fname, "-SW.")) {
		expected_parseable = 1;
		expected_fix_code  = 1;	/* Semantically suspicious */
	} else {
		fprintf(stderr, "%s: Invalid file name format\n", fname);
		return -1;
	}

	fprintf(stderr, "[=> %s]\n", fname);

	/*
	 * Perform low-level parsing.
	 */
	if(!expected_parseable)
		fprintf(stderr, "Expecting error...\n");
	asn = asn1p_parse_file(fname, parser_flags);
	if(asn == NULL) {
		if(expected_parseable) {
			fprintf(stderr, "Cannot parse file \"%s\"\n", fname);
			r_value = -1;
		} else {
			fprintf(stderr,
				"Previous error is EXPECTED, no worry\n");
		}
	} else if(!expected_parseable) {
		fprintf(stderr,
			"The file \"%s\" is not expected to be parseable, "
			"yet parsing was successfull!\n", fname);
		r_value = -1;
	}

	/*
	 * Perform semantical checks and fixes.
	 */
	if(asn && r_value == 0) {
		int ret;

		if(expected_fix_code)
			fprintf(stderr, "Expecting some problems...\n");

		ret = asn1f_process(asn, fixer_flags, 0);
		if(ret) {
			if(ret == expected_fix_code) {
				fprintf(stderr,
					"Previous error is EXPECTED, "
					"no worry\n");
			} else {
				fprintf(stderr,
					"Cannot process file \"%s\": %d\n",
					fname, ret);
				r_value = -1;
		}
		} else if(ret != expected_fix_code) {
			fprintf(stderr,
				"File \"%s\" is expected "
				"to be semantically incorrect, "
				"yet processing was successful!\n",
				fname);
			r_value = -1;
		}
	}

	/*
	 * Check validity of some values, if grammar has special
	 * instructions for that.
	 */
	if(asn && r_value == 0) {
		if(post_fix_check(asn))
			r_value = -1;
	}

	/*
	 * TODO: destroy the asn.
	 */

	return r_value;
}


static int
post_fix_check(asn1p_t *asn) {
	asn1p_module_t *mod;
	asn1p_expr_t *expr;
	int r_value = 0;

	TQ_FOR(mod, &(asn->modules), mod_next) {
		TQ_FOR(expr, &(mod->members), next) {
			assert(expr->Identifier);
			if(strncmp(expr->Identifier, "check-", 6) == 0) {
				if(post_fix_check_element(mod, expr))
					r_value = -1;
			}
		}
	}

	return r_value;
}


static int
post_fix_check_element(asn1p_module_t *mod, asn1p_expr_t *check_expr) {
	asn1p_expr_t *expr = NULL;
	char *name;
	asn1p_value_t *value;

	if(check_expr->expr_type != ASN_BASIC_INTEGER
	|| check_expr->meta_type != AMT_VALUE) {
		fprintf(stderr,
			"CHECKER: Unsupported type of \"%s\" value: "
			"%d at line %d of %s\n",
			check_expr->Identifier,
			check_expr->expr_type,
			check_expr->_lineno,
			mod->source_file_name
		);
		return -1;
	}

	assert(check_expr->meta_type == AMT_VALUE);

	value = check_expr->value;
	if(value == NULL || value->type != ATV_INTEGER) {
		fprintf(stderr,
			"CHECKER: Unsupported value type of \"%s\": "
			"%d at line %d of %s\n",
			check_expr->Identifier,
			value?(signed)value->type:-1,
			expr->_lineno,
			mod->source_file_name
		);
		return -1;
	}

	name = check_expr->Identifier + sizeof("check-") - 1;

	/*
	 * Scan in search for the original.
	 */
	TQ_FOR(expr, &(mod->members), next) {
		if(strcmp(expr->Identifier, name) == 0)
			break;
	}

	if(expr == NULL) {
		fprintf(stderr,
			"CHECKER: Value \"%s\" requested by "
			"\"check-%s\" at line %d of %s is not found!\n",
			name, name, check_expr->_lineno,
			mod->source_file_name
		);
		return -1;
	}

	if(0 && expr->expr_type != check_expr->expr_type) {
		fprintf(stderr,
			"CHECKER: Value type of \"%s\" (=%d) at line %d "
			"does not have desired type %d as requested by "
			"\"check-%s\" in %s\n",
			expr->Identifier,
			expr->expr_type,
			expr->_lineno,
			check_expr->expr_type,
			name,
			mod->source_file_name
		);
		return -1;
	}

	if(expr->value == NULL
	|| expr->value->type != value->type) {
		fprintf(stderr,
			"CHECKER: Value of \"%s\" (\"%s\", type=%d) at line %d "
			"does not have desired type %d as requested by "
			"\"check-%s\" in %s\n",
			expr->Identifier,
			asn1f_printable_value(expr->value),
			expr->value->type,
			expr->_lineno,
			value->type,
			name,
			mod->source_file_name
		);
		return -1;
	}

	assert(value->type = ATV_INTEGER);

	return 0;
}


