4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
22 * Copyright (c) 1995, 2010, Oracle and/or its affiliates. All rights reserved.
28 * This program demonstrates the use of the libelf interface to
29 * read an ELF file. pcom will open an ELF file using
30 * elf_begin(ELF_C_READ) and examine search the ELF file
31 * for a .comment section. If a .comment section is found it's
32 * contents will be displayed on stdout.
44 static const char *CommentStr
= ".comment";
47 print_comment(Elf
*elf
, const char *file
)
55 (void) printf("%s .comment:\n", file
);
57 if (elf_getshdrstrndx(elf
, &shstrndx
) == -1) {
58 (void) fprintf(stderr
, "%s: elf_getshdrstrndx() failed: %s\n",
63 while ((scn
= elf_nextscn(elf
, scn
)) != NULL
) {
65 * Do a string compare to examine each section header
66 * to see if it is a ".comment" section. If it is then
67 * this is the section we want to process.
69 if (gelf_getshdr(scn
, &shdr
) == NULL
) {
70 (void) fprintf(stderr
, "%s: elf_getshdr() failed: %s\n",
74 if (strcmp(CommentStr
, elf_strptr(elf
, shstrndx
,
75 shdr
.sh_name
)) == 0) {
80 * Get the data associated with the .comment
83 if ((data
= elf_getdata(scn
, NULL
)) == NULL
) {
84 (void) fprintf(stderr
,
85 "%s: elf_getdata() failed: %s\n",
91 * Data in a .comment section is a list of 'null'
92 * terminated strings. The following will print
93 * one string per line.
95 for (i
= 0, ptr
= (char *)data
->d_buf
;
96 i
< data
->d_size
; i
++)
101 (void) putchar('\n');
108 process_elf(Elf
*elf
, char *file
, int fd
, int member
)
113 switch (elf_kind(elf
)) {
116 * This is an ELF file, now attempt to find it's
117 * .comment section and to display it.
119 print_comment(elf
, file
);
123 * Archives contain multiple ELF files, which can each
124 * in turn be examined with libelf.
126 * The below loop will iterate over each member of the
127 * archive and recursively call process_elf().
130 while ((_elf
= elf_begin(fd
, cmd
, elf
)) != NULL
) {
134 arhdr
= elf_getarhdr(_elf
);
137 * Build up file names based off of
138 * 'archivename(membername)'.
140 (void) sprintf(buffer
, "%s(%s)", file
, arhdr
->ar_name
);
143 * Recursively process the ELF members.
145 process_elf(_elf
, buffer
, fd
, 1);
146 cmd
= elf_next(_elf
);
147 (void) elf_end(_elf
);
152 (void) fprintf(stderr
,
153 "%s: unexpected elf_kind(): 0x%x\n",
154 file
, elf_kind(elf
));
160 main(int argc
, char **argv
)
165 (void) printf("usage: %s elf_file ...\n", argv
[0]);
170 * Initialize the elf library, must be called before elf_begin()
173 if (elf_version(EV_CURRENT
) == EV_NONE
) {
174 (void) fprintf(stderr
,
175 "elf_version() failed: %s\n", elf_errmsg(0));
179 for (i
= 1; i
< argc
; i
++) {
185 if ((fd
= open(elf_fname
, O_RDONLY
)) == -1) {
191 * Attempt to open an Elf descriptor Read/Write
194 if ((elf
= elf_begin(fd
, ELF_C_READ
, 0)) == NULL
) {
195 (void) fprintf(stderr
, "elf_begin() failed: %s\n",
202 * Process each elf descriptor.
204 process_elf(elf
, elf_fname
, fd
, 0);