title: symbol lookup error: ./libobjdata.so: undefined symbol: bfd_map_over_sections
body: <p>When I compiled the getsections_dl.c file, it always output this error, does that mean I have not linked the library?</p>
  
  <p>My compile command is:</p>
  
  <pre><code>gcc getsections_dl.c -L. -ldl -lbfd -o getsections_dl
  </code></pre>
  
  <p>My getsections_dl.c:</p>
  
  <pre><code>#include &lt;stdlib.h&gt;
  #include &lt;string.h&gt;
  #include &lt;bfd.h&gt;
  #include &lt;unistd.h&gt;
  #include &lt;dlfcn.h&gt;
  
  extern void dump_sections(bfd *abfd);
  #define rdtsc(x)    __asm__ __volatile__("rdtsc \n\t" : "=A" (*(x)))
  
  
  
  // the following function is a tweaked version of the itoa functions
  // that can be found in either objsym.c or objsect.c
  char* lltoa(long long int val, int base) {
    if (val == 0x0) {
     static char zero[] = "0";
     return &amp;zero[0];
    }
    static char buf[64] = {0};
    int i = 60;
    for(; val &amp;&amp; i ; --i, val /= base)
      buf[i] = "0123456789abcdef"[val % base];
    return &amp;buf[i+1];
  }
  
  
  int main(int argc, char *argv[]) {
    bfd *obj;
    void *handle;
    unsigned long long start, finish;  
    void (*func)(bfd *);
  
    bfd_init();
  
    obj = bfd_openr(argv[1], "elf32-i386");
    if (!obj) {
      bfd_perror("open failure\n");
      return 0;
    }
  
    rdtsc(&amp;start);
  
    if (!strcmp(argv[2], "RTLD_LAZY"))
      handle = dlopen("./libobjdata.so", RTLD_LAZY);
    else
      handle = dlopen("./libobjdata.so", RTLD_NOW);
  
    rdtsc(&amp;finish);
  
    bfd_check_format(obj, bfd_object);
  
  
    //compute the cycles
    write(1, "time: ", strlen("time: "));
    int t = (finish-start)/2793;
    write(1, lltoa(t, 10), strlen(lltoa(t, 10)));
    write(1, " cycles/MHz\n\n", strlen(" cycles/MHz\n\n"));
  
  
  
    func = dlsym(handle, "dump_sections");
    // bfd_map_over_sections(obj, func2, NULL);
    dump_sections(obj);
    dlclose(handle);
  
    return 0;
  }
  </code></pre>
  
  <p>And my library C file objsect.c (which is do the something like objdump() dose):</p>
  
  <pre><code>#include &lt;bfd.h&gt;
  #include &lt;stdio.h&gt;
  #include &lt;unistd.h&gt;
  #include &lt;string.h&gt;
  
  void dump_section(bfd *abfd, asection *section, void *obj)
  {
      // Number of octets per target byte
      //unsigned int opb = bfd_octets_per_byte(abfd); 
  
  
  char* itoa(int val, int base) {
    if (val == 0x0) {
     static char zero[] = "0";
     return &amp;zero[0];
    }
    static char buf[32] = {0};
    int i = 30;
    for(; val &amp;&amp; i ; --i, val /= base)
      buf[i] = "0123456789abcdef"[val % base];
    return &amp;buf[i+1];
  }
  
  
  
  //write(1, "Section:", strlen("Section:"));
  write(1, section-&gt;name, strlen(section-&gt;name));
  write(1, " \t", strlen(" \t"));
  write(1, itoa(section-&gt;vma, 16), strlen(itoa(section-&gt;vma, 16)));
  write(1, " \t", strlen(" \t"));
  write(1, itoa(section-&gt;rawsize, 16), strlen(itoa(section-&gt;rawsize, 10)));
  write(1, " \t", strlen(" \t"));
  write(1, itoa(section-&gt;size, 16), strlen(itoa(section-&gt;size, 10)));
  write(1, " \t", strlen(" \t"));
  write(1, itoa(section-&gt;filepos, 16), strlen(itoa(section-&gt;filepos, 16)));
  write(1, " \n", strlen(" \n"));
  }
  
  void dump_sections(bfd *abfd)
  {
  
      write(1, "Name\t", strlen("Name\t"));
  
      write(1, "Size\t", strlen("Size\t"));
  
      write(1, "VMA\tt", strlen("VMA\t"));
      write(1, "LMA\t", strlen("LMA\t"));
      write(1, "File off\t", strlen("File off\t"));
      write(1, "Algn\n", strlen("Algn\n"));
  
  // For each section in abfd, call dump_section_headers()
      bfd_map_over_sections(abfd, dump_section, NULL);
  }
  </code></pre>