'Internal Documentation:
The GNU hash structure is a bit more complex than the normal hash
structure.
Again, Oracle has good documentation.
https://blogs.oracle.com/ali/entry/gnu_hash_elf_sections
You can force an ELF to use this type of symbol table by compiling
with \'gcc -Wl,--hash-style=gnu\''

def _resolve_symbol_gnu(self, libbase, symb, hshtab, strtab, symtab):

    self.status('.gnu.hash    parms')
    leak = self.leak
    Sym = {32: elf.Elf32_Sym, 64: elf.Elf64_Sym}[self.elfclass]
    nbuckets = leak.field(hshtab, elf.GNU_HASH.nbuckets)
    symndx = leak.field(hshtab, elf.GNU_HASH.symndx)
    maskwords = leak.field(hshtab, elf.GNU_HASH.maskwords)
    elfword = (self.elfclass / 8)
    buckets = ((hshtab + sizeof(elf.GNU_HASH)) + (elfword * maskwords))
    chains = (buckets + (4 * nbuckets))
    self.status('hash    chain    index')
    hsh = gnu_hash(symb)
    bucket = (hsh % nbuckets)
    ndx = leak.d(buckets, bucket)
    if (ndx == 0):
        self.failure('Empty    chain')
        return None
    chain = (chains + (4 * (ndx - symndx)))
    self.status('hash    chain')
    i = 0
    hsh &= (~ 1)
    hsh2 = 0
    while (not (hsh2 & 1)):
        hsh2 = leak.d(chain, i)
        if (hsh == (hsh2 & (~ 1))):
            sym = (symtab + (sizeof(Sym) * (ndx + i)))
            name = leak.s((strtab + leak.field(sym, Sym.st_name)))
            if (name == symb):
                offset = leak.field(sym, Sym.st_value)
                addr = (offset + libbase)
                return addr
            self.status(('%s    (hash    collision)' % name))
        i += 1
    else:
        self.failure(('Could    not    find    a    GNU    hash    that    matched    %#x' % hsh))
        return None
