Bug #644036: Counter format validation fails on Windows because the number format is I64i there.

Note: Users will run into a problem when copying a windows file to linux
and vice versa because the counter format will have to be changed on the
other operating system each time.

git-svn-id: svn+ssh://svn.gnucash.org/repo/gnucash/trunk@20382 57a11ea4-9604-0410-9ed3-97b8803252fd
This commit is contained in:
Christian Stimming 2011-03-08 11:15:07 +00:00
parent c8a5b4f0e4
commit 4506326daf
4 changed files with 96 additions and 6 deletions

View File

@ -61,6 +61,14 @@ backends (when reading the GncGUID from the data source). */
#define qof_book_set_guid(book,guid) \
qof_instance_set_guid(QOF_INSTANCE(book), guid)
/** Validate a counter format string with the given
* G_GINT64_FORMAT. Returns an error message if the format string
* was invalid, or NULL if it is ok. The caller should free the
* error message with g_free.
*/
gchar *qof_book_validate_counter_format_internal(const gchar *p,
const gchar* gint64_format);
/* @} */
/* @} */
/* @} */

View File

@ -563,7 +563,14 @@ qof_book_get_counter_format(const QofBook *book, const char *counter_name)
gchar *
qof_book_validate_counter_format(const gchar *p)
{
const gchar *conv_start, *tmp;
return qof_book_validate_counter_format_internal(p, G_GINT64_FORMAT);
}
gchar *
qof_book_validate_counter_format_internal(const gchar *p,
const gchar *gint64_format)
{
const gchar *conv_start, *tmp = NULL;
/* Validate a counter format. This is a very simple "parser" that
* simply checks for a single gint64 conversion specification,
@ -597,11 +604,23 @@ qof_book_validate_counter_format(const gchar *p)
/* Skip the % */
p++;
/* See whether we have already reached the correct format
* specification (e.g. "li" on Unix, "I64i" on Windows). */
tmp = strstr(p, gint64_format);
/* Skip any number of flag characters */
while (*p && strchr("#0- +'I", *p)) p++;
while (*p && (tmp != p) && strchr("#0- +'I", *p))
{
p++;
tmp = strstr(p, gint64_format);
}
/* Skip any number of field width digits */
while (*p && strchr("0123456789", *p)) p++;
while (*p && (tmp != p) && strchr("0123456789", *p))
{
p++;
tmp = strstr(p, gint64_format);
}
/* A precision specifier always starts with a dot */
if (*p && *p == '.')
@ -617,10 +636,10 @@ qof_book_validate_counter_format(const gchar *p)
/* See if the format string starts with the correct format
* specification. */
tmp = strstr(p, G_GINT64_FORMAT);
tmp = strstr(p, gint64_format);
if (tmp == NULL)
{
return g_strdup_printf("Invalid length modifier and/or conversion specifier ('%.2s'), it should be: " G_GINT64_FORMAT, p);
return g_strdup_printf("Invalid length modifier and/or conversion specifier ('%.4s'), it should be: %s", p, gint64_format);
}
else if (tmp != p)
{
@ -628,7 +647,7 @@ qof_book_validate_counter_format(const gchar *p)
}
/* Skip length modifier / conversion specifier */
p += strlen(G_GINT64_FORMAT);
p += strlen(gint64_format);
/* Skip a suffix of any character except % */
while (*p)

View File

@ -36,6 +36,7 @@ main (int argc,
g_type_init(); /* Initialize the GObject system */
g_test_init ( &argc, &argv, NULL ); /* initialize test program */
qof_log_init_filename_special("/dev/null"); /* Init the log system */
g_test_bug_base("https://bugzilla.gnome.org/show_bug.cgi?id="); /* init the bugzilla URL */
test_suite_qofbook();
test_suite_qofinstance();

View File

@ -23,6 +23,7 @@
#include <string.h>
#include <glib.h>
#include <qof.h>
#include "qofbook-p.h"
static const gchar *suitename = "/qof/qofbook";
void test_suite_qofbook ( void );
@ -52,9 +53,70 @@ test_book_readonly( Fixture *fixture, gconstpointer pData )
qof_book_mark_readonly( fixture->book );
g_assert( qof_book_is_readonly( fixture->book ) );
}
static void
test_book_validate_counter( void )
{
gchar *r;
g_test_bug("644036");
/* Test for detection of missing format conversion */
r = qof_book_validate_counter_format("This string is missing the conversion specifier");
g_assert(r);
if (r && g_test_verbose())
{
g_test_message("Counter format validation correctly failed: %s", r);
}
g_free(r);
/* Test the usual Linux/Unix G_GINT64_FORMAT */
r = qof_book_validate_counter_format_internal("Test - %li", "li");
if (r && g_test_verbose())
{
g_test_message("Counter format validation erroneously failed: %s", r);
}
g_assert(r == NULL);
g_free(r);
/* Test the Windows G_GINT64_FORMAT */
r = qof_book_validate_counter_format_internal("Test - %I64i", "I64i");
if (r && g_test_verbose())
{
g_test_message("Counter format validation erroneously failed: %s", r);
}
g_assert(r == NULL);
g_free(r);
/* Test the system's GINT64_FORMAT */
r = qof_book_validate_counter_format("Test - %" G_GINT64_FORMAT);
if (r && g_test_verbose())
{
g_test_message("Counter format validation erroneously failed: %s", r);
}
g_assert(r == NULL);
g_free(r);
/* Test an erroneous Windows G_GINT64_FORMAT */
r = qof_book_validate_counter_format_internal("Test - %li", "I64i");
if (r && g_test_verbose())
{
g_test_message("Counter format validation correctly failed: %s", r);
}
g_assert(r);
g_free(r);
/* Test an erroneous Linux G_GINT64_FORMAT */
r = qof_book_validate_counter_format_internal("Test - %I64i", "li");
if (r && g_test_verbose())
{
g_test_message("Counter format validation correctly failed: %s", r);
}
g_assert(r);
g_free(r);
}
void
test_suite_qofbook ( void )
{
g_test_add( suitename, Fixture, NULL, setup, test_book_readonly, teardown );
g_test_add_func( suitename, test_book_validate_counter );
}