LCOV - code coverage report
Current view: top level - libgnucash/engine - qofutil.cpp (source / functions) Coverage Total Hit
Test: gnucash.info Lines: 33.7 % 98 33
Test Date: 2025-02-07 16:25:45 Functions: 40.0 % 10 4
Legend: Lines: hit not hit | Branches: + taken - not taken # not executed Branches: - 0 0

             Branch data     Line data    Source code
       1                 :             : /********************************************************************\
       2                 :             :  * qofutil.c -- QOF utility functions                               *
       3                 :             :  * Copyright (C) 1997 Robin D. Clark                                *
       4                 :             :  * Copyright (C) 1997-2001,2004 Linas Vepstas <linas@linas.org>     *
       5                 :             :  * Copyright 2006  Neil Williams  <linux@codehelp.co.uk>            *
       6                 :             :  *                                                                  *
       7                 :             :  * This program is free software; you can redistribute it and/or    *
       8                 :             :  * modify it under the terms of the GNU General Public License as   *
       9                 :             :  * published by the Free Software Foundation; either version 2 of   *
      10                 :             :  * the License, or (at your option) any later version.              *
      11                 :             :  *                                                                  *
      12                 :             :  * This program is distributed in the hope that it will be useful,  *
      13                 :             :  * but WITHOUT ANY WARRANTY; without even the implied warranty of   *
      14                 :             :  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the    *
      15                 :             :  * GNU General Public License for more details.                     *
      16                 :             :  *                                                                  *
      17                 :             :  * You should have received a copy of the GNU General Public License*
      18                 :             :  * along with this program; if not, contact:                        *
      19                 :             :  *                                                                  *
      20                 :             :  * Free Software Foundation           Voice:  +1-617-542-5942       *
      21                 :             :  * 51 Franklin Street, Fifth Floor    Fax:    +1-617-542-2652       *
      22                 :             :  * Boston, MA  02110-1301,  USA       gnu@gnu.org                   *
      23                 :             :  *                                                                  *
      24                 :             :  *   Author: Rob Clark (rclark@cs.hmc.edu)                          *
      25                 :             :  *   Author: Linas Vepstas (linas@linas.org)                        *
      26                 :             : \********************************************************************/
      27                 :             : 
      28                 :             : #include <config.h>
      29                 :             : 
      30                 :             : #include <ctype.h>
      31                 :             : #include <glib.h>
      32                 :             : #include <stdlib.h>
      33                 :             : #include <string.h>
      34                 :             : #include "qof.h"
      35                 :             : #include "qof-backend.hpp"
      36                 :             : 
      37                 :             : G_GNUC_UNUSED static QofLogModule log_module = QOF_MOD_UTIL;
      38                 :             : 
      39                 :             : void
      40                 :           0 : g_hash_table_foreach_sorted(GHashTable *hash_table, GHFunc func, gpointer user_data, GCompareFunc compare_func)
      41                 :             : {
      42                 :             :     GList *iter;
      43                 :           0 :     GList *keys = g_list_sort(g_hash_table_get_keys(hash_table), compare_func);
      44                 :             : 
      45                 :           0 :     for (iter = keys; iter; iter = iter->next)
      46                 :             :     {
      47                 :           0 :         func(iter->data, g_hash_table_lookup(hash_table, iter->data), user_data);
      48                 :             :     }
      49                 :             : 
      50                 :           0 :     g_list_free(keys);
      51                 :           0 : }
      52                 :             : 
      53                 :             : gboolean
      54                 :         367 : qof_utf8_substr_nocase (const gchar *haystack, const gchar *needle)
      55                 :             : {
      56                 :             :     gchar *haystack_casefold, *haystack_normalized;
      57                 :             :     gchar *needle_casefold, *needle_normalized;
      58                 :             :     gchar *p;
      59                 :             : 
      60                 :         367 :     g_return_val_if_fail (haystack && needle, FALSE);
      61                 :             : 
      62                 :         367 :     haystack_casefold = g_utf8_casefold (haystack, -1);
      63                 :         367 :     haystack_normalized = g_utf8_normalize (haystack_casefold, -1,
      64                 :             :                                             G_NORMALIZE_NFC);
      65                 :         367 :     g_free (haystack_casefold);
      66                 :             : 
      67                 :         367 :     needle_casefold = g_utf8_casefold (needle, -1);
      68                 :         367 :     needle_normalized = g_utf8_normalize (needle_casefold, -1, G_NORMALIZE_NFC);
      69                 :         367 :     g_free (needle_casefold);
      70                 :             : 
      71                 :         367 :     p = strstr (haystack_normalized, needle_normalized);
      72                 :         367 :     g_free (haystack_normalized);
      73                 :         367 :     g_free (needle_normalized);
      74                 :             : 
      75                 :         367 :     return p != NULL;
      76                 :             : }
      77                 :             : 
      78                 :             : /** Use g_utf8_casefold and g_utf8_collate to compare two utf8 strings,
      79                 :             :  * ignore case. Return < 0 if da compares before db, 0 if they compare
      80                 :             :  * equal, > 0 if da compares after db. */
      81                 :             : static gint
      82                 :           0 : qof_utf8_strcasecmp (const gchar *da, const gchar *db)
      83                 :             : {
      84                 :             :     gchar *da_casefold, *db_casefold;
      85                 :             :     gint retval;
      86                 :             : 
      87                 :           0 :     g_return_val_if_fail (da != NULL, 0);
      88                 :           0 :     g_return_val_if_fail (db != NULL, 0);
      89                 :             : 
      90                 :           0 :     da_casefold = g_utf8_casefold (da, -1);
      91                 :           0 :     db_casefold = g_utf8_casefold (db, -1);
      92                 :           0 :     retval = g_utf8_collate (da_casefold, db_casefold);
      93                 :           0 :     g_free (da_casefold);
      94                 :           0 :     g_free (db_casefold);
      95                 :             : 
      96                 :           0 :     return retval;
      97                 :             : }
      98                 :             : 
      99                 :             : gint
     100                 :           0 : safe_strcasecmp (const gchar * da, const gchar * db)
     101                 :             : {
     102                 :           0 :     if ((da) && (db))
     103                 :             :     {
     104                 :           0 :         if ((da) != (db))
     105                 :             :         {
     106                 :           0 :             gint retval = qof_utf8_strcasecmp ((da), (db));
     107                 :             :             /* if strings differ, return */
     108                 :           0 :             if (retval) return retval;
     109                 :             :         }
     110                 :           0 :     }
     111                 :           0 :     else if ((!(da)) && (db))
     112                 :             :     {
     113                 :           0 :         return -1;
     114                 :             :     }
     115                 :           0 :     else if ((da) && (!(db)))
     116                 :             :     {
     117                 :           0 :         return +1;
     118                 :             :     }
     119                 :           0 :     return 0;
     120                 :             : }
     121                 :             : 
     122                 :             : gint
     123                 :          18 : null_strcmp (const gchar * da, const gchar * db)
     124                 :             : {
     125                 :          18 :     if (da && db) return strcmp (da, db);
     126                 :           2 :     if (!da && db && 0 == db[0]) return 0;
     127                 :           2 :     if (!db && da && 0 == da[0]) return 0;
     128                 :           2 :     if (!da && db) return -1;
     129                 :           2 :     if (da && !db) return +1;
     130                 :           2 :     return 0;
     131                 :             : }
     132                 :             : 
     133                 :             : #define MAX_DIGITS 50
     134                 :             : 
     135                 :             : /* inverse of strtoul */
     136                 :             : gchar *
     137                 :           0 : ultostr (gulong val, gint base)
     138                 :             : {
     139                 :             :     gchar buf[MAX_DIGITS];
     140                 :             :     gulong broke[MAX_DIGITS];
     141                 :             :     gint i;
     142                 :           0 :     gulong places = 0, reval;
     143                 :             : 
     144                 :           0 :     if ((2 > base) || (36 < base)) return NULL;
     145                 :             : 
     146                 :             :     /* count digits */
     147                 :           0 :     places = 0;
     148                 :           0 :     for (i = 0; i < MAX_DIGITS; i++)
     149                 :             :     {
     150                 :           0 :         broke[i] = val;
     151                 :           0 :         places ++;
     152                 :           0 :         val /= base;
     153                 :           0 :         if (0 == val) break;
     154                 :             :     }
     155                 :             : 
     156                 :             :     /* normalize */
     157                 :           0 :     reval = 0;
     158                 :           0 :     for (i = places - 2; i >= 0; i--)
     159                 :             :     {
     160                 :           0 :         reval += broke[i+1];
     161                 :           0 :         reval *= base;
     162                 :           0 :         broke[i] -= reval;
     163                 :             :     }
     164                 :             : 
     165                 :             :     /* print */
     166                 :           0 :     for (i = 0; i < (gint)places; i++)
     167                 :             :     {
     168                 :           0 :         if (10 > broke[i])
     169                 :             :         {
     170                 :           0 :             buf[places-1-i] = 0x30 + broke[i];  /* ascii digit zero */
     171                 :             :         }
     172                 :             :         else
     173                 :             :         {
     174                 :           0 :             buf[places-1-i] = 0x41 - 10 + broke[i];  /* ascii capital A */
     175                 :             :         }
     176                 :             :     }
     177                 :           0 :     buf[places] = 0x0;
     178                 :             : 
     179                 :           0 :     return g_strdup (buf);
     180                 :             : }
     181                 :             : 
     182                 :             : /* =================================================================== */
     183                 :             : /* returns TRUE if the string is a number, possibly with whitespace */
     184                 :             : /* =================================================================== */
     185                 :             : 
     186                 :             : gboolean
     187                 :           0 : gnc_strisnum(const gchar *s)
     188                 :             : {
     189                 :           0 :     if (s == NULL) return FALSE;
     190                 :           0 :     if (*s == 0) return FALSE;
     191                 :             : 
     192                 :           0 :     while (*s && isspace(*s))
     193                 :           0 :         s++;
     194                 :             : 
     195                 :           0 :     if (*s == 0) return FALSE;
     196                 :           0 :     if (!isdigit(*s)) return FALSE;
     197                 :             : 
     198                 :           0 :     while (*s && isdigit(*s))
     199                 :           0 :         s++;
     200                 :             : 
     201                 :           0 :     if (*s == 0) return TRUE;
     202                 :             : 
     203                 :           0 :     while (*s && isspace(*s))
     204                 :           0 :         s++;
     205                 :             : 
     206                 :           0 :     if (*s == 0) return TRUE;
     207                 :             : 
     208                 :           0 :     return FALSE;
     209                 :             : }
     210                 :             : 
     211                 :             : /* =================================================================== */
     212                 :             : /* Return NULL if the field is whitespace (blank, tab, formfeed etc.)
     213                 :             :  * Else return pointer to first non-whitespace character. */
     214                 :             : /* =================================================================== */
     215                 :             : 
     216                 :             : G_GNUC_UNUSED static const gchar *
     217                 :           0 : qof_util_whitespace_filter (const gchar * val)
     218                 :             : {
     219                 :             :     size_t len;
     220                 :           0 :     if (!val) return NULL;
     221                 :             : 
     222                 :           0 :     len = strspn (val, "\a\b\t\n\v\f\r ");
     223                 :           0 :     if (0 == val[len]) return NULL;
     224                 :           0 :     return val + len;
     225                 :             : }
     226                 :             : 
     227                 :             : #ifdef THESE_CAN_BE_USEFUL_FOR_DEGUGGING
     228                 :             : static guint g_str_hash_KEY(gconstpointer v)
     229                 :             : {
     230                 :             :     return g_str_hash(v);
     231                 :             : }
     232                 :             : static guint g_str_hash_VAL(gconstpointer v)
     233                 :             : {
     234                 :             :     return g_str_hash(v);
     235                 :             : }
     236                 :             : static gpointer g_strdup_VAL(gpointer v)
     237                 :             : {
     238                 :             :     return g_strdup(v);
     239                 :             : }
     240                 :             : static gpointer g_strdup_KEY(gpointer v)
     241                 :             : {
     242                 :             :     return g_strdup(v);
     243                 :             : }
     244                 :             : static void g_free_VAL(gpointer v)
     245                 :             : {
     246                 :             :     return g_free(v);
     247                 :             : }
     248                 :             : static void g_free_KEY(gpointer v)
     249                 :             : {
     250                 :             :     return g_free(v);
     251                 :             : }
     252                 :             : static gboolean qof_util_str_equal(gconstpointer v, gconstpointer v2)
     253                 :             : {
     254                 :             :     return (v && v2) ? g_str_equal(v, v2) : FALSE;
     255                 :             : }
     256                 :             : #endif
     257                 :             : 
     258                 :             : void
     259                 :         115 : qof_init (void)
     260                 :             : {
     261                 :         115 :     qof_log_init();
     262                 :         115 :     qof_string_cache_init();
     263                 :         115 :     qof_object_initialize ();
     264                 :         115 :     qof_query_init ();
     265                 :         115 :     qof_book_register ();
     266                 :         115 : }
     267                 :             : 
     268                 :             : void
     269                 :          42 : qof_close(void)
     270                 :             : {
     271                 :          42 :     qof_query_shutdown ();
     272                 :          42 :     qof_object_shutdown ();
     273                 :          42 :     QofBackend::release_backends();
     274                 :          42 :     qof_string_cache_destroy ();
     275                 :          42 :     qof_log_shutdown();
     276                 :          42 : }
     277                 :             : 
     278                 :             : /* ************************ END OF FILE ***************************** */
        

Generated by: LCOV version 2.0-1