Branch data Line data Source code
1 : : /* Conversion functions for versioning information. 2 : : Copyright (C) 2006, 2007 Red Hat, Inc. 3 : : Copyright (C) 2023, Mark J. Wielaard <mark@klomp.org> 4 : : This file is part of elfutils. 5 : : Written by Ulrich Drepper <drepper@redhat.com>, 2006. 6 : : 7 : : This file is free software; you can redistribute it and/or modify 8 : : it under the terms of either 9 : : 10 : : * the GNU Lesser General Public License as published by the Free 11 : : Software Foundation; either version 3 of the License, or (at 12 : : your option) any later version 13 : : 14 : : or 15 : : 16 : : * the GNU General Public License as published by the Free 17 : : Software Foundation; either version 2 of the License, or (at 18 : : your option) any later version 19 : : 20 : : or both in parallel, as here. 21 : : 22 : : elfutils is distributed in the hope that it will be useful, but 23 : : WITHOUT ANY WARRANTY; without even the implied warranty of 24 : : MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 25 : : General Public License for more details. 26 : : 27 : : You should have received copies of the GNU General Public License and 28 : : the GNU Lesser General Public License along with this program. If 29 : : not, see <http://www.gnu.org/licenses/>. */ 30 : : 31 : : #include <assert.h> 32 : : #include <gelf.h> 33 : : 34 : : #include "libelfP.h" 35 : : 36 : : 37 : : static void 38 : 130 : elf_cvt_gnuhash (void *dest, const void *src, size_t len, int encode) 39 : : { 40 : 130 : size_t size = len; 41 : : /* The GNU hash table format on 64 bit machines mixes 32 bit and 64 bit 42 : : words. We must detangle them here. */ 43 : 130 : Elf32_Word *dest32 = dest; 44 : 130 : const Elf32_Word *src32 = src; 45 : : 46 : : /* First four control words, 32 bits. */ 47 [ + + ]: 650 : for (unsigned int cnt = 0; cnt < 4; ++cnt) 48 : : { 49 [ - + ]: 520 : if (len < 4) 50 : 0 : goto done; 51 : 520 : dest32[cnt] = bswap_32 (src32[cnt]); 52 : : len -= 4; 53 : : } 54 : : 55 [ + + ]: 130 : Elf32_Word bitmask_words = encode ? src32[2] : dest32[2]; 56 : : 57 : : /* Now the 64 bit words. */ 58 : 130 : Elf64_Xword *dest64 = (Elf64_Xword *) &dest32[4]; 59 : 130 : const Elf64_Xword *src64 = (const Elf64_Xword *) &src32[4]; 60 [ + + ]: 260 : for (unsigned int cnt = 0; cnt < bitmask_words; ++cnt) 61 : : { 62 [ - + ]: 130 : if (len < 8) 63 : 0 : goto done; 64 : 130 : dest64[cnt] = bswap_64 (src64[cnt]); 65 : 130 : len -= 8; 66 : : } 67 : : 68 : : /* The rest are 32 bit words again. */ 69 : 130 : src32 = (const Elf32_Word *) &src64[bitmask_words]; 70 : 130 : dest32 = (Elf32_Word *) &dest64[bitmask_words]; 71 [ + + ]: 282 : while (len >= 4) 72 : : { 73 : 152 : *dest32++ = bswap_32 (*src32++); 74 : 152 : len -= 4; 75 : : } 76 : : 77 : 130 : done: 78 : : /* If there are any bytes left, we weren't able to convert the 79 : : partial structures, just copy them over. */ 80 [ - + ]: 130 : if (len > 0) 81 : 0 : memmove (dest + size - len, src + size - len, len); 82 : 130 : }