#include "asn1c_internal.h"
#include "asn1c_compat.h"
#include "asn1c_fdeps.h"
#include "asn1c_lang.h"
#include "asn1c_misc.h"
#include "asn1c_save.h"
#include "asn1c_out.h"

static int asn1c_dump_streams(arg_t *arg, asn1c_fdeps_t *);
static int asn1c_print_streams(arg_t *arg);
static int asn1c_save_streams(arg_t *arg, asn1c_fdeps_t *);
static int asn1c_copy_over(arg_t *arg, char *path);

int
asn1c_save_compiled_output(arg_t *arg, const char *datadir) {
	asn1c_fdeps_t *deps = 0;
	FILE *mkf;
	asn1c_fdeps_t *dlist;

	deps = asn1c_read_file_dependencies(arg, datadir);
	if(!deps && datadir) {
		WARNING("Cannot read file-dependencies information "
			"from %s\n", datadir);
	}

	TQ_FOR(arg->mod, &(arg->asn->modules), mod_next) {
		TQ_FOR(arg->expr, &(arg->mod->members), next) {
			if(asn1_lang_map[arg->expr->meta_type]
				[arg->expr->expr_type].type_cb) {
				if(asn1c_dump_streams(arg, deps))
					return -1;
			}
		}
	}

	/*
	 * Dump out the Makefile template and the rest of the support code.
	 */
	if((arg->flags & A1C_PRINT_COMPILED)
	|| (arg->flags & A1C_OMIT_SUPPORT_CODE)) {
		return 0;	/* Finished */
	}

	mkf = asn1c_open_file("Makefile.am", ".sample");
	if(mkf == NULL) {
		perror("Makefile.am.sample");
		return -1;
	}

	fprintf(mkf, "ASN_MODULE_SOURCES=");
	TQ_FOR(arg->mod, &(arg->asn->modules), mod_next) {
		TQ_FOR(arg->expr, &(arg->mod->members), next) {
			if(asn1_lang_map[arg->expr->meta_type]
				[arg->expr->expr_type].type_cb) {
				fprintf(mkf, "\t\\\n\t%s.c",
				arg->expr->Identifier);
			}
		}
	}
	fprintf(mkf, "\n\nASN_MODULE_HEADERS=");
	TQ_FOR(arg->mod, &(arg->asn->modules), mod_next) {
		TQ_FOR(arg->expr, &(arg->mod->members), next) {
			if(asn1_lang_map[arg->expr->meta_type]
				[arg->expr->expr_type].type_cb) {
				fprintf(mkf, "\t\\\n\t%s.h",
				arg->expr->Identifier);
			}
		}
	}
	fprintf(mkf, "\n\n");

	/*
	 * Move necessary skeleton files and add them to Makefile.am.sample.
	 */
	dlist = asn1c_deps_makelist(deps);
	if(dlist) {
		char buf[8129];
		char *dir_end;
		size_t dlen = strlen(datadir);
		int i;

		assert(dlen < (sizeof(buf) / 2 - 2));
		memcpy(buf, datadir, dlen);
		dir_end = buf + dlen;
		*dir_end++ = '/';

		for(i = 0; i < dlist->el_count; i++) {
			char *fname = dlist->elements[i]->filename;
			char *dotH;

			assert(strlen(fname) < (sizeof(buf) / 2));
			strcpy(dir_end, fname);

			if(asn1c_copy_over(arg, buf) == -1) {
				fprintf(mkf, ">>>ABORTED<<<");
				fclose(mkf);
				return -1;
			}
			dotH = strrchr(fname, 'h');
			if(dotH && fname<dotH && dotH[-1] == '.' && !dotH[1]) {
				fprintf(mkf, "ASN_MODULE_HEADERS+=%s\n", fname);
			} else {
				fprintf(mkf, "ASN_MODULE_SOURCES+=%s\n", fname);
			}
		}
	}

	fprintf(mkf, "\n\n"
		"lib_LTLIBRARIES=libsomething.la\n"
		"libsomething_la_SOURCES="
			"$(ASN_MODULE_SOURCES) $(ASN_MODULE_HEADERS)\n"
		"\n"
		"# This file may be used as an input for make(3)\n"
		"# Remove the lines below to convert it into a pure .am file\n"
		"TARGET = progname\n"
		"CFLAGS += -I.\n"
		"OBJS=${ASN_MODULE_SOURCES:.c=.o} $(TARGET).o\n"
		"\nall: $(TARGET)\n"
		"\n$(TARGET): ${OBJS}"
		"\n\t$(CC) $(CFLAGS) -o $(TARGET) ${OBJS} $(LDFLAGS) $(LIBS)\n"
		"\n.SUFFIXES:"
		"\n.SUFFIXES: .c .o\n"
		"\n.c.o:"
		"\n\t$(CC) $(CFLAGS) -o $@ -c $<\n"
		"\nclean:"
		"\n\trm -f $(TARGET)"
		"\n\trm -f $(OBJS)\n"
		"\n"
	);
	fclose(mkf);
	fprintf(stderr, "Generated Makefile.am.sample\n");

	return 0;
}

/*
 * Dump the streams.
 */
static int
asn1c_dump_streams(arg_t *arg, asn1c_fdeps_t *deps)  {
	if(arg->flags & A1C_PRINT_COMPILED) {
		return asn1c_print_streams(arg);
	} else {
		return asn1c_save_streams(arg, deps);
	}
}

static int
asn1c_print_streams(arg_t *arg)  {
	compiler_streams_t *cs = arg->expr->data;
	asn1p_expr_t *expr = arg->expr;
	int i;

	for(i = 1; i < OT_MAX; i++) {
		out_chunk_t *ot;
		if(TQ_FIRST(&cs->destination[i].chunks) == NULL)
			continue;

		printf("\n/*** <<< %s [%s] >>> ***/\n\n",
			_compiler_stream2str[i],
			expr->Identifier);

		TQ_FOR(ot, &(cs->destination[i].chunks), next) {
			fwrite(ot->buf, ot->len, 1, stdout);
		}
	}

	return 0;
}

static int
asn1c_save_streams(arg_t *arg, asn1c_fdeps_t *deps) {
	asn1p_expr_t *expr = arg->expr;
	compiler_streams_t *cs = expr->data;
	out_chunk_t *ot;
	FILE *fp_c, *fp_h;
	char *header_id;

	if(cs == NULL) {
		fprintf(stderr, "Cannot compile %s at line %d\n",
			expr->Identifier, expr->_lineno);
		return -1;
	}

	fp_c = asn1c_open_file(expr->Identifier, ".c");
	fp_h = asn1c_open_file(expr->Identifier, ".h");
	if(fp_c == NULL || fp_h == NULL) {
		if(fp_c) fclose(fp_c);	/* lacks unlink() */
		if(fp_h) fclose(fp_h);	/* lacks unlink() */
		return -1;
	}

	fprintf(fp_c,
	"/*\n"
	" * Generated by asn1c-" VERSION " (http://lionet.info/asn1c)\n"
	" * From ASN.1 module \"%s\"\n"
	" * \tfound in \"%s\"\n"
	" */\n\n",
		arg->mod->Identifier,
		arg->mod->source_file_name
	);
	fprintf(fp_h,
	"/*\n"
	" * Generated by asn1c-" VERSION " (http://lionet.info/asn1c)\n"
	" * From ASN.1 module \"%s\"\n"
	" * \tfound in \"%s\"\n"
	" */\n\n",
		arg->mod->Identifier,
		arg->mod->source_file_name
	);

	header_id = asn1c_make_identifier(0, expr->Identifier, NULL);
	fprintf(fp_h,
		"#ifndef\t_%s_H_\n"
		"#define\t_%s_H_\n"
		"\n", header_id, header_id);

	fprintf(fp_h, "#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n");

	fprintf(fp_h, "#include <asn_application.h>\n\n");

	TQ_FOR(ot, &(cs->destination[OT_INCLUDES].chunks), next) {
		asn1c_activate_dependency(deps, 0, ot->buf);
		fwrite(ot->buf, ot->len, 1, fp_h);
	}
	fprintf(fp_h, "\n");
	TQ_FOR(ot, &(cs->destination[OT_DEPS].chunks), next)
		fwrite(ot->buf, ot->len, 1, fp_h);
	fprintf(fp_h, "\n");
	TQ_FOR(ot, &(cs->destination[OT_TYPE_DECLS].chunks), next)
		fwrite(ot->buf, ot->len, 1, fp_h);
	fprintf(fp_h, "\n");
	TQ_FOR(ot, &(cs->destination[OT_FUNC_DECLS].chunks), next)
		fwrite(ot->buf, ot->len, 1, fp_h);

	fprintf(fp_h, "\n#ifdef __cplusplus\n}\n#endif\n\n"
			"#endif\t/* _%s_H_ */\n",
		header_id);

	fprintf(fp_c, "#include <asn_internal.h>\n\n");
	fprintf(fp_c, "#include <%s.h>\n\n", expr->Identifier);	/* Myself */
	TQ_FOR(ot, &(cs->destination[OT_CTABLES].chunks), next)
		fwrite(ot->buf, ot->len, 1, fp_c);
	TQ_FOR(ot, &(cs->destination[OT_CODE].chunks), next)
		fwrite(ot->buf, ot->len, 1, fp_c);
	TQ_FOR(ot, &(cs->destination[OT_STAT_DEFS].chunks), next)
		fwrite(ot->buf, ot->len, 1, fp_c);

	assert(OT_MAX == 8);

	fclose(fp_c);
	fclose(fp_h);
	fprintf(stderr, "Compiled %s.c\n", expr->Identifier);
	fprintf(stderr, "Compiled %s.h\n", expr->Identifier);
	return 0;
}

/*
 * Copy file for real.
 */
static int
real_copy(const char *src, const char *dst) {
	unsigned char buf[8192];
	FILE *fpsrc, *fpdst;
	size_t len;
	int retval = 0;

	fpsrc = fopen(src, "rb");
	if(!fpsrc) { errno = EIO; return -1; }
	fpdst = fopen(src, "wb");
	if(!fpdst) { fclose(fpsrc); errno = EIO; return -1; }

	while(!feof(fpsrc)) {
		len = fread(buf, 1, sizeof(buf), fpsrc);
		if(fwrite(buf, 1, len, fpsrc) != len) {
			errno = EIO;
			retval = -1;
			break;
		}
	}

	fclose(fpsrc);
	fclose(fpdst);
	return retval;
}

static int
asn1c_copy_over(arg_t *arg, char *path) {
	char *fname;

	(void)arg;	/* Unused argument */

	fname = a1c_basename(path);
	if(!fname
#ifdef	WIN32
		|| real_copy(path, fname)
#else
		|| (1 ? symlink(path, fname) : real_copy(path, fname))
#endif
	) {
		if(errno == EEXIST) {
			struct stat sb1, sb2;
			if(stat(path, &sb1) == 0
			&& stat(fname, &sb2) == 0
			&& sb1.st_dev == sb2.st_dev
			&& sb1.st_ino == sb2.st_ino) {
				/*
				 * Nothing to do.
				 */
				fprintf(stderr,
					"File %s is already here as %s\n",
					path, fname);
				return 1;
			} else {
				fprintf(stderr,
					"Retaining local %s (%s suggested)\n",
					fname, path);
				return 1;
			}
		} else if(errno == ENOENT) {
			/* Ignore this */
			return 0;
		} else {
			fprintf(stderr, "Symlink %s -> %s failed: %s\n",
				path, fname, strerror(errno));
			return -1;
		}
	}

	fprintf(stderr, "Symlinked %s\t-> %s\n", path, fname);

	return 1;
}

