1 /* Copyright (C) 2002 Red Hat, Inc. 2 Written by Ulrich Drepper <drepper (at) redhat.com>, 2002. 3 4 This program is Open Source software; you can redistribute it and/or 5 modify it under the terms of the Open Software License version 1.0 as 6 published by the Open Source Initiative. 7 8 You should have received a copy of the Open Software License along 9 with this program; if not, you may obtain a copy of the Open Software 10 License version 1.0 from http://www.opensource.org/licenses/osl.php or 11 by writing the Open Source Initiative c/o Lawrence Rosen, Esq., 12 3001 King Ranch Road, Ukiah, CA 95482. */ 13 14 #include <fcntl.h> 15 #include <inttypes.h> 16 #include <libasm.h> 17 #include <libelf.h> 18 #include <stdio.h> 19 #include <unistd.h> 20 21 22 static const char fname[] = "asm-tst8-out.o"; 23 24 25 int 26 main (void) 27 { 28 int result = 0; 29 size_t cnt; 30 AsmCtx_t *ctx; 31 Elf *elf; 32 int fd; 33 34 elf_version (EV_CURRENT); 35 36 ctx = asm_begin (fname, false, EM_386, ELFCLASS32, ELFDATA2LSB); 37 if (ctx == NULL) 38 { 39 printf ("cannot create assembler context: %s\n", asm_errmsg (-1)); 40 return 1; 41 } 42 43 if (asm_newabssym (ctx, "tst8-out.s", 4, 0xfeedbeef, STT_FILE, STB_LOCAL) 44 == NULL) 45 { 46 printf ("cannot create absolute symbol: %s\n", asm_errmsg (-1)); 47 asm_abort (ctx); 48 return 1; 49 } 50 51 /* Create the output file. */ 52 if (asm_end (ctx) != 0) 53 { 54 printf ("cannot create output file: %s\n", asm_errmsg (-1)); 55 asm_abort (ctx); 56 return 1; 57 } 58 59 /* Check the file. */ 60 fd = open (fname, O_RDONLY); 61 if (fd == -1) 62 { 63 printf ("cannot open generated file: %m\n"); 64 result = 1; 65 goto out; 66 } 67 68 elf = elf_begin (fd, ELF_C_READ, NULL); 69 if (elf == NULL) 70 { 71 printf ("cannot create ELF descriptor: %s\n", elf_errmsg (-1)); 72 result = 1; 73 goto out_close; 74 } 75 if (elf_kind (elf) != ELF_K_ELF) 76 { 77 puts ("not a valid ELF file"); 78 result = 1; 79 goto out_close2; 80 } 81 82 for (cnt = 1; 1; ++cnt) 83 { 84 Elf_Scn *scn; 85 GElf_Shdr shdr_mem; 86 GElf_Shdr *shdr; 87 88 scn = elf_getscn (elf, cnt); 89 if (scn == NULL) 90 { 91 printf ("cannot get section %Zd: %s\n", cnt, elf_errmsg (-1)); 92 result = 1; 93 continue; 94 } 95 96 shdr = gelf_getshdr (scn, &shdr_mem); 97 if (shdr == NULL) 98 { 99 printf ("cannot get section header for section %Zd: %s\n", 100 cnt, elf_errmsg (-1)); 101 result = 1; 102 continue; 103 } 104 /* We are looking for the symbol table. */ 105 if (shdr->sh_type != SHT_SYMTAB) 106 continue; 107 108 for (cnt = 1; cnt< (shdr->sh_size 109 / gelf_fsize (elf, ELF_T_SYM, 1, EV_CURRENT)); 110 ++cnt) 111 { 112 GElf_Sym sym_mem; 113 GElf_Sym *sym; 114 115 if (cnt > 1) 116 { 117 puts ("too many symbol"); 118 result = 1; 119 break; 120 } 121 122 sym = gelf_getsym (elf_getdata (scn, NULL), cnt, &sym_mem); 123 if (sym == NULL) 124 { 125 printf ("cannot get symbol %zu: %s\n", cnt, elf_errmsg (-1)); 126 result = 1; 127 } 128 else 129 { 130 if (sym->st_shndx != SHN_ABS) 131 { 132 printf ("expected common symbol, got section %u\n", 133 (unsigned int) sym->st_shndx); 134 result = 1; 135 } 136 137 if (sym->st_value != 0xfeedbeef) 138 { 139 printf ("requested value 0xfeedbeef, is %#" PRIxMAX "\n", 140 (uintmax_t) sym->st_value); 141 result = 1; 142 } 143 144 if (sym->st_size != 4) 145 { 146 printf ("requested size 4, is %" PRIuMAX "\n", 147 (uintmax_t) sym->st_value); 148 result = 1; 149 } 150 151 if (GELF_ST_TYPE (sym->st_info) != STT_FILE) 152 { 153 printf ("requested type FILE, is %u\n", 154 (unsigned int) GELF_ST_TYPE (sym->st_info)); 155 result = 1; 156 } 157 } 158 } 159 160 break; 161 } 162 163 out_close2: 164 elf_end (elf); 165 out_close: 166 close (fd); 167 out: 168 /* We don't need the file anymore. */ 169 unlink (fname); 170 171 return result; 172 } 173