GnuCash  4.8a-132-gcdaeb421d+
Files | Macros | Functions

Files

file  qof-string-cache.h
 QOF String cache functions.
 
file  qofutil.h
 QOF utility functions.
 

Macros

#define QOF_MOD_UTIL   "qof.utilities"
 
#define CACHE_INSERT(str)   qof_string_cache_insert((str))
 
#define CACHE_REMOVE(str)   qof_string_cache_remove((str))
 
#define CACHE_REPLACE(dst, src)
 
#define QOF_CACHE_NEW(void)   qof_string_cache_insert("")
 
#define QOF_MOD_UTIL   "qof.utilities"
 Do not use these for printf, only scanf.
 
#define stpcpy   g_stpcpy
 

Functions

void qof_string_cache_init (void)
 The QOF String Cache: More...
 
void qof_string_cache_destroy (void)
 Destroy the qof_string_cache.
 
void qof_string_cache_remove (const char *key)
 You can use this function as a destroy notifier for a GHashTable that uses common strings as keys (or values, for that matter.)
 
const char * qof_string_cache_insert (const char *key)
 You can use this function with g_hash_table_insert(), for the key (or value), as long as you use the destroy notifier above.
 
const char * qof_string_cache_replace (const char *dst, const char *src)
 Same as CACHE_REPLACE below, but safe to call from C++.
 
void g_hash_table_foreach_sorted (GHashTable *hash_table, GHFunc func, gpointer user_data, GCompareFunc compare_func)
 Calls the given function for each of the key/value pairs in the GHashTable in an order determined by the GCompareFunc applied to the keys. More...
 
gboolean qof_utf8_substr_nocase (const gchar *haystack, const gchar *needle)
 Search for an occurrence of the substring needle in the string haystack, ignoring case. More...
 
gint safe_strcasecmp (const gchar *da, const gchar *db)
 case sensitive comparison of strings da and db - either may be NULL. More...
 
gint null_strcmp (const gchar *da, const gchar *db)
 The null_strcmp compares strings a and b the same way that strcmp() does, except that either may be null. More...
 
gchar * ultostr (gulong val, gint base)
 The ultostr() subroutine is the inverse of strtoul(). More...
 
gboolean gnc_strisnum (const gchar *s)
 Returns true if string s is a number, possibly surrounded by whitespace. More...
 
gboolean qof_begin_edit (QofInstance *inst)
 begin_edit More...
 
gboolean qof_commit_edit (QofInstance *inst)
 commit_edit helpers More...
 
gboolean qof_commit_edit_part2 (QofInstance *inst, void(*on_error)(QofInstance *, QofBackendError), void(*on_done)(QofInstance *), void(*on_free)(QofInstance *))
 part2 – deal with the backend More...
 

typedef enum as string macros

#define ENUM_BODY(name, value)   name value,
 
#define AS_STRING_CASE(name, value)   case name: { return #name; }
 
#define FROM_STRING_CASE(name, value)
 
#define DEFINE_ENUM(name, list)
 
#define AS_STRING_DEC(name, list)   const gchar* name##asString(name n);
 
#define AS_STRING_FUNC(name, list)
 
#define FROM_STRING_DEC(name, list)
 
#define FROM_STRING_FUNC(name, list)
 

enum as string with no typedef

Similar but used when the enum is NOT a typedef Make sure you use the DEFINE_ENUM_NON_TYPEDEF macro.

You can precede the FROM_STRING_FUNC_NON_TYPEDEF and AS_STRING_FUNC_NON_TYPEDEF macros with the keyword static if appropriate.

ENUM_BODY is used in both types.

#define DEFINE_ENUM_NON_TYPEDEF(name, list)
 
#define FROM_STRING_DEC_NON_TYPEDEF(name, list)
 
#define FROM_STRING_CASE_NON_TYPEDEF(name, value)   if (strcmp(str, #name) == 0) { *type = name; }
 
#define FROM_STRING_FUNC_NON_TYPEDEF(name, list)
 
#define AS_STRING_DEC_NON_TYPEDEF(name, list)   const gchar* name##asString(enum name n);
 
#define AS_STRING_FUNC_NON_TYPEDEF(name, list)
 
#define AS_STRING_CASE_NON_TYPEDEF(name, value)   case name: { return #name; }
 

Convenience wrappers

void qof_init (void)
 Initialise the Query Object Framework. More...
 
void qof_close (void)
 Safely close down the Query Object Framework. More...
 

Detailed Description

Macro Definition Documentation

◆ AS_STRING_FUNC

#define AS_STRING_FUNC (   name,
  list 
)
Value:
const gchar* name##asString(name n) { \
switch (n) { \
list(AS_STRING_CASE) \
default: return ""; } }

Definition at line 87 of file qofutil.h.

◆ AS_STRING_FUNC_NON_TYPEDEF

#define AS_STRING_FUNC_NON_TYPEDEF (   name,
  list 
)
Value:
const gchar* name##asString(enum name n) { \
switch (n) { \
list(AS_STRING_CASE_NON_TYPEDEF) \
default: return ""; } }

Definition at line 140 of file qofutil.h.

◆ CACHE_REPLACE

#define CACHE_REPLACE (   dst,
  src 
)
Value:
do { \
const char *tmp = CACHE_INSERT((src)); \
CACHE_REMOVE((dst)); \
(dst) = tmp; \
} while (0)

Definition at line 103 of file qof-string-cache.h.

◆ DEFINE_ENUM

#define DEFINE_ENUM (   name,
  list 
)
Value:
typedef enum { \
list(ENUM_BODY) \
}name;

Definition at line 79 of file qofutil.h.

◆ DEFINE_ENUM_NON_TYPEDEF

#define DEFINE_ENUM_NON_TYPEDEF (   name,
  list 
)
Value:
enum name { \
list(ENUM_BODY) \
};

Definition at line 119 of file qofutil.h.

◆ FROM_STRING_CASE

#define FROM_STRING_CASE (   name,
  value 
)
Value:
if (strcmp(str, #name) == 0) { \
return name; }

Definition at line 75 of file qofutil.h.

◆ FROM_STRING_DEC

#define FROM_STRING_DEC (   name,
  list 
)
Value:
name name##fromString \
(const gchar* str);

Definition at line 93 of file qofutil.h.

◆ FROM_STRING_DEC_NON_TYPEDEF

#define FROM_STRING_DEC_NON_TYPEDEF (   name,
  list 
)
Value:
void name##fromString \
(const gchar* str, enum name *type);

Definition at line 124 of file qofutil.h.

◆ FROM_STRING_FUNC

#define FROM_STRING_FUNC (   name,
  list 
)
Value:
name name##fromString \
(const gchar* str) { \
if(str == NULL) { return 0; } \
list(FROM_STRING_CASE) \
return 0; }

Definition at line 97 of file qofutil.h.

◆ FROM_STRING_FUNC_NON_TYPEDEF

#define FROM_STRING_FUNC_NON_TYPEDEF (   name,
  list 
)
Value:
void name##fromString \
(const gchar* str, enum name *type) { \
if(str == NULL) { return; } \
list(FROM_STRING_CASE_NON_TYPEDEF) }

Definition at line 131 of file qofutil.h.

Function Documentation

◆ g_hash_table_foreach_sorted()

void g_hash_table_foreach_sorted ( GHashTable *  hash_table,
GHFunc  func,
gpointer  user_data,
GCompareFunc  compare_func 
)

Calls the given function for each of the key/value pairs in the GHashTable in an order determined by the GCompareFunc applied to the keys.

The function is passed the key and value of each pair, and the given user_data parameter.

Definition at line 40 of file qofutil.cpp.

41 {
42  GList *iter;
43  GList *keys = g_list_sort(g_hash_table_get_keys(hash_table), compare_func);
44 
45  for (iter = keys; iter; iter = iter->next)
46  {
47  func(iter->data, g_hash_table_lookup(hash_table, iter->data), user_data);
48  }
49 
50  g_list_free(keys);
51 }

◆ gnc_strisnum()

gboolean gnc_strisnum ( const gchar *  s)

Returns true if string s is a number, possibly surrounded by whitespace.

Definition at line 187 of file qofutil.cpp.

188 {
189  if (s == NULL) return FALSE;
190  if (*s == 0) return FALSE;
191 
192  while (*s && isspace(*s))
193  s++;
194 
195  if (*s == 0) return FALSE;
196  if (!isdigit(*s)) return FALSE;
197 
198  while (*s && isdigit(*s))
199  s++;
200 
201  if (*s == 0) return TRUE;
202 
203  while (*s && isspace(*s))
204  s++;
205 
206  if (*s == 0) return TRUE;
207 
208  return FALSE;
209 }

◆ null_strcmp()

gint null_strcmp ( const gchar *  da,
const gchar *  db 
)

The null_strcmp compares strings a and b the same way that strcmp() does, except that either may be null.

This routine assumes that a null string is equal to the empty string.

Definition at line 123 of file qofutil.cpp.

124 {
125  if (da && db) return strcmp (da, db);
126  if (!da && db && 0 == db[0]) return 0;
127  if (!db && da && 0 == da[0]) return 0;
128  if (!da && db) return -1;
129  if (da && !db) return +1;
130  return 0;
131 }

◆ qof_begin_edit()

gboolean qof_begin_edit ( QofInstance *  inst)

begin_edit

Parameters
instan instance of QofInstance

The caller should use this macro first and then perform any other operations.

Definition at line 951 of file qofinstance.cpp.

952 {
953  QofInstancePrivate *priv;
954 
955  if (!inst) return FALSE;
956 
957  priv = GET_PRIVATE(inst);
958  priv->editlevel++;
959  if (1 < priv->editlevel) return FALSE;
960  if (0 >= priv->editlevel)
961  priv->editlevel = 1;
962 
963  auto be = qof_book_get_backend(priv->book);
964  if (be)
965  be->begin(inst);
966  else
967  priv->dirty = TRUE;
968 
969  return TRUE;
970 }
QofBackend * qof_book_get_backend(const QofBook *book)
Retrieve the backend used by this book.
Definition: qofbook.cpp:524

◆ qof_close()

void qof_close ( void  )

Safely close down the Query Object Framework.

Use in place of separate close / shutdown functions (like qof_query_shutdown(), etc.) to protect against future changes.

Definition at line 269 of file qofutil.cpp.

270 {
271  qof_query_shutdown ();
272  qof_object_shutdown ();
273  QofBackend::release_backends();
276 }
void qof_string_cache_destroy(void)
Destroy the qof_string_cache.
void qof_log_shutdown(void)
Be nice, close the logfile if possible.
Definition: qoflog.cpp:268

◆ qof_commit_edit()

gboolean qof_commit_edit ( QofInstance *  inst)

commit_edit helpers

The caller should call PART1 as the first thing, then perform any local operations prior to calling the backend. Then call PART2. part1 – deal with the editlevel

Parameters
instan instance of QofInstance

Definition at line 972 of file qofinstance.cpp.

973 {
974  QofInstancePrivate *priv;
975 
976  if (!inst) return FALSE;
977 
978  priv = GET_PRIVATE(inst);
979  priv->editlevel--;
980  if (0 < priv->editlevel) return FALSE;
981 
982  if (0 > priv->editlevel)
983  {
984  PERR ("unbalanced call - resetting (was %d)", priv->editlevel);
985  priv->editlevel = 0;
986  }
987  return TRUE;
988 }
#define PERR(format, args...)
Log a serious error.
Definition: qoflog.h:244

◆ qof_commit_edit_part2()

gboolean qof_commit_edit_part2 ( QofInstance *  inst,
void(*)(QofInstance *, QofBackendError on_error,
void(*)(QofInstance *)  on_done,
void(*)(QofInstance *)  on_free 
)

part2 – deal with the backend

Parameters
instan instance of QofInstance
on_errora function called if there is a backend error. void (*on_error)(inst, QofBackendError)
on_donea function called after the commit is completed successfully for an object which remained valid. void (*on_done)(inst)
on_freea function called if the commit succeeded and the instance is to be freed. void (*on_free)(inst)

Note that only one callback will be called (or zero, if that callback is NULL). In particular, 'on_done' will not be called for an object which is to be freed.

Returns TRUE, if the commit succeeded, FALSE otherwise.

Definition at line 991 of file qofinstance.cpp.

995 {
996  QofInstancePrivate *priv;
997 
998  priv = GET_PRIVATE(inst);
999 
1000  if (priv->dirty &&
1001  !(priv->infant && priv->do_free)) {
1002  qof_collection_mark_dirty(priv->collection);
1003  qof_book_mark_session_dirty(priv->book);
1004  }
1005 
1006  /* See if there's a backend. If there is, invoke it. */
1007  auto be = qof_book_get_backend(priv->book);
1008  if (be)
1009  {
1010  QofBackendError errcode;
1011 
1012  /* clear errors */
1013  do
1014  {
1015  errcode = be->get_error();
1016  }
1017  while (errcode != ERR_BACKEND_NO_ERR);
1018 
1019  be->commit(inst);
1020  errcode = be->get_error();
1021  if (errcode != ERR_BACKEND_NO_ERR)
1022  {
1023  /* XXX Should perform a rollback here */
1024  priv->do_free = FALSE;
1025 
1026  /* Push error back onto the stack */
1027  be->set_error (errcode);
1028  if (on_error)
1029  on_error(inst, errcode);
1030  return FALSE;
1031  }
1032  if (!priv->dirty) //Cleared if the save was successful
1033  priv->infant = FALSE;
1034  }
1035 
1036  if (priv->do_free)
1037  {
1038  if (on_free)
1039  on_free(inst);
1040  return TRUE;
1041  }
1042 
1043  if (on_done)
1044  on_done(inst);
1045  return TRUE;
1046 }
QofBackendError
The errors that can be reported to the GUI & other front-end users.
Definition: qofbackend.h:57
void qof_book_mark_session_dirty(QofBook *book)
The qof_book_mark_dirty() routine marks the book as having been modified.
Definition: qofbook.cpp:481
QofBackend * qof_book_get_backend(const QofBook *book)
Retrieve the backend used by this book.
Definition: qofbook.cpp:524
QofCollection * collection
Entity collection.
Definition: qofinstance.cpp:78

◆ qof_init()

void qof_init ( void  )

Initialise the Query Object Framework.

Use in place of separate init functions (like qof_query_init(), etc.) to protect against future changes.

Definition at line 259 of file qofutil.cpp.

260 {
261  qof_log_init();
263  qof_object_initialize ();
264  qof_query_init ();
265  qof_book_register ();
266 }
void qof_log_init(void)
Initialize the error logging subsystem.
Definition: qoflog.cpp:160
void qof_query_init(void)
Subsystem initialization and shutdown.
Definition: qofquery.cpp:1343
void qof_string_cache_init(void)
The QOF String Cache:

◆ qof_string_cache_init()

void qof_string_cache_init ( void  )

The QOF String Cache:

Many strings used throughout QOF and QOF applications are likely to be duplicated.

QOF provides a reference counted cache system for the strings, which shares strings whenever possible.

Use qof_string_cache_insert to insert a string into the cache (it will return a pointer to the cached string). Basically you should use this instead of g_strdup.

Use qof_string_cache_remove (giving it a pointer to a cached string) if the string is unused. If this is the last reference to the string it will be removed from the cache, otherwise it will just decrement the reference count. Basically you should use this instead of g_free.

Just in case it's not clear: The remove function must NOT be called for the string you passed INTO the insert function. It must be called for the cached string that is returned by the insert function.

Note that all the work is done when inserting or removing. Once cached the strings are just plain C strings.

The string cache is demand-created on first use.Initialize the string cache

Definition at line 67 of file qof-string-cache.cpp.

68 {
69  (void)qof_get_string_cache();
70 }

◆ qof_utf8_substr_nocase()

gboolean qof_utf8_substr_nocase ( const gchar *  haystack,
const gchar *  needle 
)

Search for an occurrence of the substring needle in the string haystack, ignoring case.

Return TRUE if one is found or FALSE otherwise.

Definition at line 54 of file qofutil.cpp.

55 {
56  gchar *haystack_casefold, *haystack_normalized;
57  gchar *needle_casefold, *needle_normalized;
58  gchar *p;
59 
60  g_return_val_if_fail (haystack && needle, FALSE);
61 
62  haystack_casefold = g_utf8_casefold (haystack, -1);
63  haystack_normalized = g_utf8_normalize (haystack_casefold, -1,
64  G_NORMALIZE_ALL);
65  g_free (haystack_casefold);
66 
67  needle_casefold = g_utf8_casefold (needle, -1);
68  needle_normalized = g_utf8_normalize (needle_casefold, -1, G_NORMALIZE_ALL);
69  g_free (needle_casefold);
70 
71  p = strstr (haystack_normalized, needle_normalized);
72  g_free (haystack_normalized);
73  g_free (needle_normalized);
74 
75  return p != NULL;
76 }

◆ safe_strcasecmp()

gint safe_strcasecmp ( const gchar *  da,
const gchar *  db 
)

case sensitive comparison of strings da and db - either may be NULL.

A non-NULL string is greater than a NULL string.

Parameters
dastring 1.
dbstring 2.
Returns
If da == NULL && db != NULL, returns -1. If da != NULL && db == NULL, returns +1. If da != NULL && db != NULL, returns the result of strcmp(da, db). If da == NULL && db == NULL, returns 0.

Definition at line 100 of file qofutil.cpp.

101 {
102  if ((da) && (db))
103  {
104  if ((da) != (db))
105  {
106  gint retval = qof_utf8_strcasecmp ((da), (db));
107  /* if strings differ, return */
108  if (retval) return retval;
109  }
110  }
111  else if ((!(da)) && (db))
112  {
113  return -1;
114  }
115  else if ((da) && (!(db)))
116  {
117  return +1;
118  }
119  return 0;
120 }

◆ ultostr()

gchar* ultostr ( gulong  val,
gint  base 
)

The ultostr() subroutine is the inverse of strtoul().

It accepts a number and prints it in the indicated base. The returned string should be g_freed when done.

Definition at line 137 of file qofutil.cpp.

138 {
139  gchar buf[MAX_DIGITS];
140  gulong broke[MAX_DIGITS];
141  gint i;
142  gulong places = 0, reval;
143 
144  if ((2 > base) || (36 < base)) return NULL;
145 
146  /* count digits */
147  places = 0;
148  for (i = 0; i < MAX_DIGITS; i++)
149  {
150  broke[i] = val;
151  places ++;
152  val /= base;
153  if (0 == val) break;
154  }
155 
156  /* normalize */
157  reval = 0;
158  for (i = places - 2; i >= 0; i--)
159  {
160  reval += broke[i+1];
161  reval *= base;
162  broke[i] -= reval;
163  }
164 
165  /* print */
166  for (i = 0; i < (gint)places; i++)
167  {
168  if (10 > broke[i])
169  {
170  buf[places-1-i] = 0x30 + broke[i]; /* ascii digit zero */
171  }
172  else
173  {
174  buf[places-1-i] = 0x41 - 10 + broke[i]; /* ascii capital A */
175  }
176  }
177  buf[places] = 0x0;
178 
179  return g_strdup (buf);
180 }