#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <fcntl.h>
#include <libelf.h>
#include "defs.h"
#include "conv.h"
#include "sgs.h"
int fflag = 0,
Fflag = 0,
nflag = 0;
int numbase = DECIMAL;
static int errflag = 0;
int oneflag = 0;
int exitcode = 0;
char *fname;
char *archive;
int is_archive = 0;
static char *tool_name;
static void usagerr();
#define OPTSTR "VoxnfF"
#define GETOPTSTR "VoxnfF?"
static Elf *elf;
static Elf_Arhdr *arhdr;
int
main(int argc, char ** argv, char ** envp)
{
extern void error();
extern void process();
extern int numbase;
extern int errflag;
extern int oneflag;
extern int optind;
extern char *fname;
int c;
static int fd;
extern char *archive;
Elf_Cmd cmd;
Elf *arf;
unsigned Vflag = 0;
tool_name = argv[0];
while ((c = getopt(argc, argv, GETOPTSTR)) != EOF) {
switch (c) {
case 'o':
if (numbase != HEX)
numbase = OCTAL;
else
(void) fprintf(stderr,
"size: -x set, -o ignored\n");
break;
case 'd':
numbase = DECIMAL;
break;
case 'x':
if (numbase != OCTAL)
numbase = HEX;
else
(void) fprintf(stderr,
"size: -o set, -x ignored\n");
break;
case 'f':
fflag++;
break;
case 'F':
Fflag++;
break;
case 'n':
nflag++;
break;
case 'V':
(void) fprintf(stderr, "size: %s %s\n",
(const char *)SGU_PKG,
(const char *)SGU_REL);
Vflag++;
break;
case '?':
errflag++;
break;
default:
break;
}
}
if (errflag || (optind >= argc)) {
if (!(Vflag && (argc == 2) && !errflag)) {
usagerr();
}
}
if ((argc - optind) == 1) {
oneflag++;
}
if (elf_version(EV_CURRENT) == EV_NONE) {
(void) fprintf(stderr, "size: Libelf is out of date");
exit(FATAL);
}
for (; optind < argc; optind++) {
fname = argv[optind];
if ((fd = open(argv[optind], O_RDONLY)) == -1) {
error(fname, "cannot open");
} else {
cmd = ELF_C_READ;
arf = 0;
if ((arf = elf_begin(fd, cmd, arf)) == 0) {
(void) fprintf(stderr,
"size: %s: %s\n", fname, elf_errmsg(-1));
return (FATAL);
}
if (elf_kind(arf) == ELF_K_AR) {
archive = argv[optind];
} else {
archive = "";
}
while ((elf = elf_begin(fd, cmd, arf)) != 0) {
if ((arhdr = elf_getarhdr(elf)) == 0) {
if (elf_kind(arf) == ELF_K_NONE) {
(void) fprintf(stderr,
"%s: %s: invalid file type\n",
tool_name, fname);
exitcode++;
break;
} else {
process(elf);
}
} else if (arhdr->ar_name[0] != '/') {
fname = arhdr->ar_name;
if (elf_kind(arf) == ELF_K_NONE) {
(void) fprintf(stderr,
"%s: %s[%s]: invalid file type\n",
tool_name, archive, fname);
exitcode++;
break;
} else {
is_archive++;
process(elf);
}
}
cmd = elf_next(elf);
(void) elf_end(elf);
}
(void) elf_end(arf);
(void) close(fd);
}
}
if (exitcode)
exit(FATAL);
else
exit(0);
return (0);
}
static void
usagerr()
{
(void) fprintf(stderr,
"usage: %s [-%s] file(s)...\n", tool_name, OPTSTR);
exitcode++;
}