LCOV - code coverage report
Current view: top level - cmdline - util.h (source / functions) Hit Total Coverage
Test: lcov.info Lines: 39 41 95.1 %
Date: 2026-04-29 15:04:44 Functions: 7 7 100.0 %

          Line data    Source code
       1             : // SPDX-License-Identifier: GPL-3.0-or-later
       2             : // Copyright (C) 2011 Andrea Mazzoleni
       3             : 
       4             : #ifndef __UTIL_H
       5             : #define __UTIL_H
       6             : 
       7             : 
       8             : /****************************************************************************/
       9             : /* memory */
      10             : 
      11             : /**
      12             :  * Safe aligned malloc.
      13             :  * If no memory is available, it aborts.
      14             :  */
      15             : void* malloc_nofail_align(size_t size, void** freeptr);
      16             : 
      17             : /**
      18             :  * Safe aligned malloc. Usable for direct io.
      19             :  */
      20             : void* malloc_nofail_direct(size_t size, void** freeptr);
      21             : 
      22             : /**
      23             :  * Safe aligned vector allocation.
      24             :  * If no memory is available, it aborts.
      25             :  */
      26             : void** malloc_nofail_vector_align(int nd, int n, size_t size, void** freeptr);
      27             : 
      28             : /**
      29             :  * Safe page vector allocation. Usable for direct io.
      30             :  * If no memory is available, it aborts.
      31             :  */
      32             : void** malloc_nofail_vector_direct(int nd, int n, size_t size, void** freeptr);
      33             : 
      34             : /**
      35             :  * Safe allocation with memory test.
      36             :  */
      37             : void* malloc_nofail_test(size_t size);
      38             : 
      39             : /**
      40             :  * Test the memory vector for RAM problems.
      41             :  * If a problem is found, it crashes.
      42             :  */
      43             : void mtest_vector(int n, size_t size, void** vv);
      44             : 
      45             : /****************************************************************************/
      46             : /* crc */
      47             : 
      48             : /**
      49             :  * CRC initial value.
      50             :  * Using a not zero value allows to detect a leading run of zeros.
      51             :  */
      52             : #define CRC_IV 0xffffffffU
      53             : 
      54             : /**
      55             :  * CRC-32 (Castagnoli) table.
      56             :  */
      57             : extern uint32_t CRC32C_0[256];
      58             : extern uint32_t CRC32C_1[256];
      59             : extern uint32_t CRC32C_2[256];
      60             : extern uint32_t CRC32C_3[256];
      61             : 
      62             : /**
      63             :  * If the CPU support the CRC instructions.
      64             :  */
      65             : #if HAVE_SSE42
      66             : extern int crc_x86;
      67             : #endif
      68             : 
      69             : /**
      70             :  * Compute CRC-32 (Castagnoli) for a single byte without the IV.
      71             :  */
      72     4202652 : static inline uint32_t crc32c_plain_char(uint32_t crc, unsigned char c)
      73             : {
      74             : #if HAVE_SSE42
      75     4202652 :         if (tommy_likely(crc_x86)) {
      76     4202652 :                 asm ("crc32b %1, %0\n" : "+r" (crc) : "m" (c));
      77     4202652 :                 return crc;
      78             :         }
      79             : #endif
      80           0 :         return CRC32C_0[(crc ^ c) & 0xff] ^ (crc >> 8);
      81             : }
      82             : 
      83             : /**
      84             :  * Compute the CRC-32 (Castagnoli) without the IV.
      85             :  */
      86         361 : static inline uint32_t crc32c_gen_plain(uint32_t crc, const unsigned char* ptr, unsigned size)
      87             : {
      88    22544912 :         while (size >= 4) {
      89    22544551 :                 crc ^= ptr[0] | (uint32_t)ptr[1] << 8 | (uint32_t)ptr[2] << 16 | (uint32_t)ptr[3] << 24;
      90    22544551 :                 crc = CRC32C_3[crc & 0xff] ^ CRC32C_2[(crc >> 8) & 0xff] ^ CRC32C_1[(crc >> 16) & 0xff] ^ CRC32C_0[crc >> 24];
      91    22544551 :                 ptr += 4;
      92    22544551 :                 size -= 4;
      93             :         }
      94             : 
      95         370 :         while (size) {
      96           9 :                 crc = CRC32C_0[(crc ^ *ptr) & 0xff] ^ (crc >> 8);
      97           9 :                 ++ptr;
      98           9 :                 --size;
      99             :         }
     100             : 
     101         361 :         return crc;
     102             : }
     103             : 
     104             : /**
     105             :  * Compute the CRC-32 (Castagnoli) without the IV.
     106             :  */
     107             : #if HAVE_SSE42
     108    23874767 : static inline uint32_t crc32c_x86_plain(uint32_t crc, const unsigned char* ptr, unsigned size)
     109             : {
     110             : #ifdef CONFIG_X86_64
     111    23874767 :         uint64_t crc64 = crc;
     112   238439925 :         while (size >= 8) {
     113   214565158 :                 asm ("crc32q %1, %0\n" : "+r" (crc64) : "m" (*(const uint64_t*)ptr));
     114   214565158 :                 ptr += 8;
     115   214565158 :                 size -= 8;
     116             :         }
     117    23874767 :         crc = crc64;
     118             : #else
     119             :         while (size >= 4) {
     120             :                 asm ("crc32l %1, %0\n" : "+r" (crc) : "m" (*(const uint32_t*)ptr));
     121             :                 ptr += 4;
     122             :                 size -= 4;
     123             :         }
     124             : #endif
     125    74776955 :         while (size) {
     126    50902188 :                 asm ("crc32b %1, %0\n" : "+r" (crc) : "m" (*ptr));
     127    50902188 :                 ++ptr;
     128    50902188 :                 --size;
     129             :         }
     130             : 
     131    23874767 :         return crc;
     132             : }
     133             : #endif
     134             : 
     135             : /**
     136             :  * Compute CRC-32 (Castagnoli) without the IV.
     137             :  */
     138    23225887 : static inline uint32_t crc32c_plain(uint32_t crc, const unsigned char* ptr, unsigned size)
     139             : {
     140             : #if HAVE_SSE42
     141    23225887 :         if (tommy_likely(crc_x86)) {
     142    23225887 :                 return crc32c_x86_plain(crc, ptr, size);
     143             :         }
     144             : #endif
     145           0 :         return crc32c_gen_plain(crc, ptr, size);
     146             : }
     147             : 
     148             : /**
     149             :  * Compute the CRC-32 (Castagnoli)
     150             :  */
     151             : extern uint32_t (*crc32c)(uint32_t crc, const unsigned char* ptr, unsigned size);
     152             : 
     153             : /**
     154             :  * Internal entry points for testing.
     155             :  */
     156             : uint32_t crc32c_gen(uint32_t crc, const unsigned char* ptr, unsigned size);
     157             : uint32_t crc32c_x86(uint32_t crc, const unsigned char* ptr, unsigned size);
     158             : 
     159             : /**
     160             :  * Initialize the CRC-32 (Castagnoli) support.
     161             :  */
     162             : void crc32c_init(void);
     163             : 
     164             : /****************************************************************************/
     165             : /* hash */
     166             : 
     167             : /**
     168             :  * Size of the hash.
     169             :  */
     170             : #define HASH_MAX 16
     171             : 
     172             : /**
     173             :  * Hash kinds.
     174             :  */
     175             : #define HASH_UNDEFINED 0
     176             : #define HASH_MURMUR3 1
     177             : #define HASH_SPOOKY2 2
     178             : #define HASH_METRO 3
     179             : #define HASH_MUSEAIR 4
     180             : 
     181             : /**
     182             :  * Return the hash that is expected to be the fastest in this architecture
     183             :  */
     184             : unsigned membesthash(void);
     185             : 
     186             : /**
     187             :  * Return the name of the hash
     188             :  */
     189             : const char* memhashname(unsigned kind);
     190             : 
     191             : /**
     192             :  * Compute the HASH of a memory block.
     193             :  * Seed is a 128 bit vector.
     194             :  */
     195             : void memhash(unsigned kind, const unsigned char* seed, void* digest, const void* src, size_t size);
     196             : 
     197             : /**
     198             :  * Return the hash name.
     199             :  */
     200             : const char* hash_config_name(unsigned kind);
     201             : 
     202             : /**
     203             :  * Count the number of different bits in the two buffers.
     204             :  */
     205             : unsigned memdiff(const unsigned char* data1, const unsigned char* data2, size_t size);
     206             : 
     207             : /**
     208             :  * Unit test
     209             :  */
     210             : int util_selftest(void);
     211             : 
     212             : /****************************************************************************/
     213             : /* lock */
     214             : 
     215             : /**
     216             :  * Create and locks the lock file.
     217             :  * Return -1 on error, otherwise it's the file handle to pass to lock_unlock().
     218             :  */
     219             : int lock_lock(const char* file);
     220             : 
     221             : /**
     222             :  * Unlock the lock file.
     223             :  * Return -1 on error.
     224             :  */
     225             : int lock_unlock(int f);
     226             : 
     227             : /****************************************************************************/
     228             : /* bitvect */
     229             : 
     230             : typedef unsigned char bit_vect_t;
     231             : #define BIT_VECT_SIZE (sizeof(bit_vect_t) * 8)
     232             : 
     233         244 : static inline size_t bit_vect_size(size_t max)
     234             : {
     235         244 :         return (max + BIT_VECT_SIZE - 1) / BIT_VECT_SIZE;
     236             : }
     237             : 
     238     1111724 : static inline void bit_vect_set(bit_vect_t* bit_vect, size_t off)
     239             : {
     240     1111724 :         bit_vect_t mask = 1 << (off % BIT_VECT_SIZE);
     241     1111724 :         bit_vect[off / BIT_VECT_SIZE] |= mask;
     242     1111724 : }
     243             : 
     244             : static inline void bit_vect_clear(bit_vect_t* bit_vect, size_t off)
     245             : {
     246             :         bit_vect_t mask = 1 << (off % BIT_VECT_SIZE);
     247             :         bit_vect[off / BIT_VECT_SIZE] &= ~mask;
     248             : }
     249             : 
     250     1503708 : static inline int bit_vect_test(bit_vect_t* bit_vect, size_t off)
     251             : {
     252     1503708 :         bit_vect_t mask = 1 << (off % BIT_VECT_SIZE);
     253     1503708 :         return (bit_vect[off / BIT_VECT_SIZE] & mask) != 0;
     254             : }
     255             : 
     256             : /****************************************************************************/
     257             : /* muldiv */
     258             : 
     259             : unsigned muldiv(uint64_t v, uint64_t mul, uint64_t div);
     260             : unsigned muldiv_upper(uint64_t v, uint64_t mul, uint64_t div);
     261             : 
     262             : #endif
     263             : 

Generated by: LCOV version 1.0