view ticoff/basics.c @ 73:10f3fbff5e97

tiobjd: symbol table parsing implemented
author Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
date Tue, 25 Mar 2014 18:34:03 +0000
parents 6799a5c57a49
children 2eef88395908
line wrap: on
line source

/*
 * This C module implements the "basics" of TI COFF image analysis.
 */

#include <sys/types.h>
#include <sys/file.h>
#include <sys/stat.h>
#include <sys/mman.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <time.h>
#include "filestruct.h"
#include "globals.h"

mmap_objfile()
{
	int fd;
	struct stat st;

	fd = open(objfilename, O_RDONLY);
	if (fd < 0) {
		perror(objfilename);
		exit(1);
	}
	fstat(fd, &st);
	if (!S_ISREG(st.st_mode)) {
		fprintf(stderr, "error: %s is not a regular file\n",
			objfilename);
		exit(1);
	}
	objfile_tot_size = st.st_size;
	filemap = mmap(NULL, objfile_tot_size, PROT_READ, MAP_PRIVATE, fd, 0L);
	if (filemap == MAP_FAILED) {
		perror("mmap");
		exit(1);
	}
	close(fd);
}

unsigned
get_u16(ptr)
	u_char *ptr;
{
	return ptr[0] | ptr[1] << 8;
}

get_s16(ptr)
	u_char *ptr;
{
	int i;

	i = ptr[0] | ptr[1] << 8;
	if (i >= 32768)
		i -= 65536;
	return(i);
}

unsigned
get_u32(ptr)
	u_char *ptr;
{
	return ptr[0] | ptr[1] << 8 | ptr[2] << 16 | ptr[3] << 24;
}

initial_parse_hdr()
{
	unsigned symtab_offset;

	filehdr_struct = (struct external_filehdr *) filemap;
	if (get_u16(filehdr_struct->f_magic) != 0xC2) {
		fprintf(stderr, "error: %s is not a TI COFF2 object\n",
			objfilename);
		exit(1);
	}
	if (get_u16(filehdr_struct->f_target_id) != 0x97) {
		fprintf(stderr, "error: TI COFF object %s is not for TMS470\n",
			objfilename);
		exit(1);
	}
	if (get_u16(filehdr_struct->f_opthdr)) {
		fprintf(stderr,
			"error: %s has the \"optional\" header present\n",
			objfilename);
		exit(1);
	}
	sections_raw = (struct external_scnhdr *)
				(filemap + sizeof(struct external_filehdr));
	nsections = get_u16(filehdr_struct->f_nscns);
	symtab_offset = get_u32(filehdr_struct->f_symptr);
	symtab_raw = (struct external_syment *)(filemap + symtab_offset);
	nsymtab = get_u32(filehdr_struct->f_nsyms);
	strtab_offset = symtab_offset +
				sizeof(struct external_syment) * nsymtab;
}

dump_filehdr_info()
{
	time_t timestamp;
	struct tm *timedec;

	timestamp = get_u32(filehdr_struct->f_timdat);
	timedec = gmtime(&timestamp);
	printf("timestamp: %d-%02d-%02dT%02d:%02d:%02dZ\n",
		timedec->tm_year + 1900, timedec->tm_mon + 1, timedec->tm_mday,
		timedec->tm_hour, timedec->tm_min, timedec->tm_sec);
	printf("file flags: 0x%x\n", get_u16(filehdr_struct->f_flags));
	printf("%u sections, %u symtab entries\n", nsections, nsymtab);
	return(0);
}