-#include <stdio.h>
-#include <stdarg.h>
-#include <stdlib.h>
-#include <stdint.h>
-#include <inttypes.h>
-#include <string.h>
-#include <errno.h>
-#include <unistd.h>
-#include <elf.h>
-#include <byteswap.h>
-#define USE_BSD
-#include <endian.h>
-#include <regex.h>
-#include <tools/le_byteshift.h>
+/* This is included from relocs_32/64.c */
 
 #define ElfW(type)             _ElfW(ELF_BITS, type)
 #define _ElfW(bits, type)      __ElfW(bits, type)
 #define __ElfW(bits, type)     Elf##bits##_##type
 
-#ifndef ELF_BITS
-#define ELF_BITS               32
-#endif
-
-#if (ELF_BITS == 64)
-#define ELF_MACHINE             EM_X86_64
-#define ELF_MACHINE_NAME        "x86_64"
-#define SHT_REL_TYPE            SHT_RELA
-#define Elf_Rel                 Elf64_Rela
-#else
-#define ELF_MACHINE            EM_386
-#define ELF_MACHINE_NAME       "i386"
-#define SHT_REL_TYPE           SHT_REL
-#define Elf_Rel                        ElfW(Rel)
-#endif
-
-#if (ELF_BITS == 64)
-#define ELF_CLASS               ELFCLASS64
-#define ELF_R_SYM(val)          ELF64_R_SYM(val)
-#define ELF_R_TYPE(val)         ELF64_R_TYPE(val)
-#define ELF_ST_TYPE(o)          ELF64_ST_TYPE(o)
-#define ELF_ST_BIND(o)          ELF64_ST_BIND(o)
-#define ELF_ST_VISIBILITY(o)    ELF64_ST_VISIBILITY(o)
-#else
-#define ELF_CLASS              ELFCLASS32
-#define ELF_R_SYM(val)         ELF32_R_SYM(val)
-#define ELF_R_TYPE(val)                ELF32_R_TYPE(val)
-#define ELF_ST_TYPE(o)         ELF32_ST_TYPE(o)
-#define ELF_ST_BIND(o)         ELF32_ST_BIND(o)
-#define ELF_ST_VISIBILITY(o)   ELF32_ST_VISIBILITY(o)
-#endif
-
 #define Elf_Addr               ElfW(Addr)
 #define Elf_Ehdr               ElfW(Ehdr)
 #define Elf_Phdr               ElfW(Phdr)
 #define Elf_Shdr               ElfW(Shdr)
 #define Elf_Sym                        ElfW(Sym)
 
-static void die(char *fmt, ...);
-
-#define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0]))
 static Elf_Ehdr ehdr;
 
 struct relocs {
 };
 static struct section *secs;
 
-enum symtype {
-       S_ABS,
-       S_REL,
-       S_SEG,
-       S_LIN,
-       S_NSYMTYPES
-};
-
 static const char * const sym_regex_kernel[S_NSYMTYPES] = {
 /*
  * Following symbols have been audited. There values are constant and do
        "^(xen_irq_disable_direct_reloc$|"
        "xen_save_fl_direct_reloc$|"
        "VDSO|"
-#if (ELF_BITS == 64)
+#if ELF_BITS == 64
        "__vvar_page|"
 #endif
        "__crc_)",
        "__end_rodata|"
        "__initramfs_start|"
        "(jiffies|jiffies_64)|"
-#if (ELF_BITS == 64)
+#if ELF_BITS == 64
        "__per_cpu_load|"
        "init_per_cpu__.*|"
        "__end_rodata_hpage_align|"
         }
 }
 
-static void die(char *fmt, ...)
-{
-       va_list ap;
-       va_start(ap, fmt);
-       vfprintf(stderr, fmt, ap);
-       va_end(ap);
-       exit(1);
-}
-
 static const char *sym_type(unsigned type)
 {
        static const char *type_name[] = {
 {
        static const char *type_name[] = {
 #define REL_TYPE(X) [X] = #X
-#if (ELF_BITS == 64)
+#if ELF_BITS == 64
                REL_TYPE(R_X86_64_NONE),
                REL_TYPE(R_X86_64_64),
                REL_TYPE(R_X86_64_PC32),
 #define elf_half_to_cpu(x)     elf16_to_cpu(x)
 #define elf_word_to_cpu(x)     elf32_to_cpu(x)
 
-#if (ELF_BITS == 64)
+#if ELF_BITS == 64
 static uint64_t elf64_to_cpu(uint64_t val)
 {
         return le64_to_cpu(val);
        int i;
        const char *format;
 
-       if (ehdr.e_ident[EI_CLASS] == ELFCLASS64)
+       if (ELF_BITS == 64)
                format = "%5d %016"PRIx64" %5"PRId64" %10s %10s %12s %s\n";
        else
                format = "%5d %08"PRIx32"  %5"PRId32" %10s %10s %12s %s\n";
        int i, printed = 0;
        const char *format;
 
-       if (ehdr.e_ident[EI_CLASS] == ELFCLASS64)
+       if (ELF_BITS == 64)
                format = "%016"PRIx64" %016"PRIx64" %10s %016"PRIx64"  %s\n";
        else
                format = "%08"PRIx32" %08"PRIx32" %10s %08"PRIx32"  %s\n";
        }
 }
 
+#if ELF_BITS == 64
+
 /*
  * Check to see if a symbol lies in the .data..percpu section.
  * For some as yet not understood reason the "__init_begin"
                strcmp(symname, "__init_begin");
 }
 
+
 static int do_reloc64(struct section *sec, Elf_Rel *rel, ElfW(Sym) *sym,
                      const char *symname)
 {
        return 0;
 }
 
+#else
 
 static int do_reloc32(struct section *sec, Elf_Rel *rel, Elf_Sym *sym,
                      const char *symname)
        return 0;
 }
 
+#endif
+
 static int cmp_relocs(const void *va, const void *vb)
 {
        const uint32_t *a, *b;
        int (*do_reloc)(struct section *sec, Elf_Rel *rel, Elf_Sym *sym,
                        const char *symname);
 
-       if (ehdr.e_ident[EI_CLASS] == ELFCLASS64)
+#if ELF_BITS == 64
+       if (!use_real_mode)
                do_reloc = do_reloc64;
-       else if (!use_real_mode)
+       else
+               die("--realmode not valid for a 64-bit ELF file");
+#else
+       if (!use_real_mode)
                do_reloc = do_reloc32;
        else
                do_reloc = do_reloc_real;
+#endif
 
        /* Collect up the relocations */
        walk_relocs(do_reloc);
                for (i = 0; i < relocs32.count; i++)
                        write_reloc(relocs32.offset[i], stdout);
        } else {
-               if (ehdr.e_ident[EI_CLASS] == ELFCLASS64) {
+               if (ELF_BITS == 64) {
                        /* Print a stop */
                        write_reloc(0, stdout);
 
        }
 }
 
-static void usage(void)
-{
-       die("relocs [--abs-syms|--abs-relocs|--text|--realmode] vmlinux\n");
-}
+#if ELF_BITS == 64
+# define process process_64
+#else
+# define process process_32
+#endif
 
-int main(int argc, char **argv)
+void process(FILE *fp, int use_real_mode, int as_text,
+            int show_absolute_syms, int show_absolute_relocs)
 {
-       int show_absolute_syms, show_absolute_relocs;
-       int as_text, use_real_mode;
-       const char *fname;
-       FILE *fp;
-       int i;
-
-       show_absolute_syms = 0;
-       show_absolute_relocs = 0;
-       as_text = 0;
-       use_real_mode = 0;
-       fname = NULL;
-       for (i = 1; i < argc; i++) {
-               char *arg = argv[i];
-               if (*arg == '-') {
-                       if (strcmp(arg, "--abs-syms") == 0) {
-                               show_absolute_syms = 1;
-                               continue;
-                       }
-                       if (strcmp(arg, "--abs-relocs") == 0) {
-                               show_absolute_relocs = 1;
-                               continue;
-                       }
-                       if (strcmp(arg, "--text") == 0) {
-                               as_text = 1;
-                               continue;
-                       }
-                       if (strcmp(arg, "--realmode") == 0) {
-                               use_real_mode = 1;
-                               continue;
-                       }
-               }
-               else if (!fname) {
-                       fname = arg;
-                       continue;
-               }
-               usage();
-       }
-       if (!fname) {
-               usage();
-       }
        regex_init(use_real_mode);
-       fp = fopen(fname, "r");
-       if (!fp) {
-               die("Cannot open %s: %s\n",
-                       fname, strerror(errno));
-       }
        read_ehdr(fp);
        read_shdrs(fp);
        read_strtabs(fp);
        read_symtabs(fp);
        read_relocs(fp);
-       if (ehdr.e_ident[EI_CLASS] == ELFCLASS64)
+       if (ELF_BITS == 64)
                percpu_init();
        if (show_absolute_syms) {
                print_absolute_symbols();
-               goto out;
+               return;
        }
        if (show_absolute_relocs) {
                print_absolute_relocs();
-               goto out;
+               return;
        }
        emit_relocs(as_text, use_real_mode);
-out:
-       fclose(fp);
-       return 0;
 }
 
--- /dev/null
+#include "relocs.h"
+
+void die(char *fmt, ...)
+{
+       va_list ap;
+       va_start(ap, fmt);
+       vfprintf(stderr, fmt, ap);
+       va_end(ap);
+       exit(1);
+}
+
+static void usage(void)
+{
+       die("relocs [--abs-syms|--abs-relocs|--text|--realmode] vmlinux\n");
+}
+
+int main(int argc, char **argv)
+{
+       int show_absolute_syms, show_absolute_relocs;
+       int as_text, use_real_mode;
+       const char *fname;
+       FILE *fp;
+       int i;
+       unsigned char e_ident[EI_NIDENT];
+
+       show_absolute_syms = 0;
+       show_absolute_relocs = 0;
+       as_text = 0;
+       use_real_mode = 0;
+       fname = NULL;
+       for (i = 1; i < argc; i++) {
+               char *arg = argv[i];
+               if (*arg == '-') {
+                       if (strcmp(arg, "--abs-syms") == 0) {
+                               show_absolute_syms = 1;
+                               continue;
+                       }
+                       if (strcmp(arg, "--abs-relocs") == 0) {
+                               show_absolute_relocs = 1;
+                               continue;
+                       }
+                       if (strcmp(arg, "--text") == 0) {
+                               as_text = 1;
+                               continue;
+                       }
+                       if (strcmp(arg, "--realmode") == 0) {
+                               use_real_mode = 1;
+                               continue;
+                       }
+               }
+               else if (!fname) {
+                       fname = arg;
+                       continue;
+               }
+               usage();
+       }
+       if (!fname) {
+               usage();
+       }
+       fp = fopen(fname, "r");
+       if (!fp) {
+               die("Cannot open %s: %s\n", fname, strerror(errno));
+       }
+       if (fread(&e_ident, 1, EI_NIDENT, fp) != EI_NIDENT) {
+               die("Cannot read %s: %s", fname, strerror(errno));
+       }
+       rewind(fp);
+       if (e_ident[EI_CLASS] == ELFCLASS64)
+               process_64(fp, use_real_mode, as_text,
+                          show_absolute_syms, show_absolute_relocs);
+       else
+               process_32(fp, use_real_mode, as_text,
+                          show_absolute_syms, show_absolute_relocs);
+       fclose(fp);
+       return 0;
+}