os/ossrv/glib/tests/sequence-test.c
author sl
Tue, 10 Jun 2014 14:32:02 +0200
changeset 1 260cb5ec6c19
permissions -rw-r--r--
Update contrib.
sl@0
     1
/* Portions copyright (c) 2009 Nokia Corporation.  All rights reserved.*/
sl@0
     2
#include <stdio.h>
sl@0
     3
#include <glib.h>
sl@0
     4
#include <stdlib.h>
sl@0
     5
#ifdef __SYMBIAN32__
sl@0
     6
#include "mrt2_glib2_test.h"
sl@0
     7
#endif /*__SYMBIAN32__*/
sl@0
     8
/* Keep this in sync with gsequence.c !!! */
sl@0
     9
typedef struct _GSequenceNode GSequenceNode;
sl@0
    10
sl@0
    11
struct _GSequence
sl@0
    12
{
sl@0
    13
  GSequenceNode *       end_node;
sl@0
    14
  GDestroyNotify        data_destroy_notify;
sl@0
    15
  gboolean              access_prohibited;
sl@0
    16
  GSequence *           real_sequence;
sl@0
    17
};
sl@0
    18
sl@0
    19
struct _GSequenceNode
sl@0
    20
{
sl@0
    21
  gint                  n_nodes;
sl@0
    22
  GSequenceNode *       parent;
sl@0
    23
  GSequenceNode *       left;
sl@0
    24
  GSequenceNode *       right;
sl@0
    25
  gpointer              data;
sl@0
    26
};
sl@0
    27
sl@0
    28
static guint
sl@0
    29
get_priority (GSequenceNode *node)
sl@0
    30
{
sl@0
    31
  guint key = GPOINTER_TO_UINT (node);
sl@0
    32
sl@0
    33
  key = (key << 15) - key - 1;
sl@0
    34
  key = key ^ (key >> 12);
sl@0
    35
  key = key + (key << 2);
sl@0
    36
  key = key ^ (key >> 4);
sl@0
    37
  key = key + (key << 3) + (key << 11);
sl@0
    38
  key = key ^ (key >> 16);
sl@0
    39
sl@0
    40
  return key? key : 1;
sl@0
    41
}
sl@0
    42
      
sl@0
    43
static void
sl@0
    44
check_node (GSequenceNode *node)
sl@0
    45
{
sl@0
    46
  if (node)
sl@0
    47
    {
sl@0
    48
      g_assert (node->parent != node);
sl@0
    49
      if (node->parent)
sl@0
    50
        g_assert (node->parent->left == node || node->parent->right == node);
sl@0
    51
      g_assert (node->n_nodes == 1 + (node->left ? node->left->n_nodes : 0) + (node->right ? node->right->n_nodes : 0));
sl@0
    52
      if (node->left)
sl@0
    53
          g_assert (get_priority (node) >= get_priority (node->left));
sl@0
    54
      if (node->right)
sl@0
    55
          g_assert (get_priority (node) >= get_priority (node->right));
sl@0
    56
      check_node (node->left);
sl@0
    57
      check_node (node->right);
sl@0
    58
    }
sl@0
    59
}
sl@0
    60
sl@0
    61
void
sl@0
    62
g_sequence_check (GSequence *seq)
sl@0
    63
{
sl@0
    64
  GSequenceNode *node = seq->end_node;
sl@0
    65
sl@0
    66
  while (node->parent)
sl@0
    67
    node = node->parent;
sl@0
    68
sl@0
    69
  check_node (node);
sl@0
    70
sl@0
    71
  while (node->right)
sl@0
    72
    node = node->right;
sl@0
    73
sl@0
    74
  g_assert (seq->end_node == node);
sl@0
    75
  g_assert (node->data == seq);
sl@0
    76
sl@0
    77
}
sl@0
    78
sl@0
    79
//undefs done here as some of these enums are already defined in s60 environ
sl@0
    80
#ifdef __SYMBIAN32__
sl@0
    81
#undef NEW 
sl@0
    82
#undef FREE
sl@0
    83
#undef GET_LENGTH
sl@0
    84
#undef FOREACH
sl@0
    85
#undef FOREACH_RANGE
sl@0
    86
#undef SORT
sl@0
    87
#undef SORT_ITER
sl@0
    88
#endif//__SYMBIAN32__
sl@0
    89
         
sl@0
    90
enum {
sl@0
    91
  NEW, FREE, GET_LENGTH, FOREACH, FOREACH_RANGE, SORT, SORT_ITER,
sl@0
    92
  
sl@0
    93
  /* Getting iters */
sl@0
    94
  GET_BEGIN_ITER, GET_END_ITER, GET_ITER_AT_POS, APPEND, PREPEND,
sl@0
    95
  INSERT_BEFORE, MOVE, SWAP, INSERT_SORTED, INSERT_SORTED_ITER, SORT_CHANGED,
sl@0
    96
  SORT_CHANGED_ITER, REMOVE, REMOVE_RANGE, MOVE_RANGE, SEARCH, SEARCH_ITER,
sl@0
    97
  
sl@0
    98
  /* dereferencing */
sl@0
    99
  GET, SET,
sl@0
   100
  
sl@0
   101
  /* operations on GSequenceIter * */
sl@0
   102
  ITER_IS_BEGIN, ITER_IS_END, ITER_NEXT, ITER_PREV, ITER_GET_POSITION,
sl@0
   103
  ITER_MOVE, ITER_GET_SEQUENCE,
sl@0
   104
  
sl@0
   105
  /* search */
sl@0
   106
  ITER_COMPARE, RANGE_GET_MIDPOINT,
sl@0
   107
  N_OPS
sl@0
   108
};
sl@0
   109
sl@0
   110
typedef struct SequenceInfo
sl@0
   111
{
sl@0
   112
  GQueue *	queue;
sl@0
   113
  GSequence *	sequence;
sl@0
   114
  int		n_items;
sl@0
   115
} SequenceInfo;
sl@0
   116
sl@0
   117
typedef struct
sl@0
   118
{
sl@0
   119
  SequenceInfo *seq;
sl@0
   120
  int		  number;
sl@0
   121
} Item;
sl@0
   122
sl@0
   123
void g_sequence_check (GSequence *sequence);
sl@0
   124
sl@0
   125
static Item *
sl@0
   126
fix_pointer (gconstpointer data)
sl@0
   127
{
sl@0
   128
  return (Item *)((char *)data - 1);
sl@0
   129
}
sl@0
   130
sl@0
   131
static Item *
sl@0
   132
get_item (GSequenceIter *iter)
sl@0
   133
{
sl@0
   134
  return fix_pointer (g_sequence_get (iter));
sl@0
   135
}
sl@0
   136
sl@0
   137
static void
sl@0
   138
check_integrity (SequenceInfo *info)
sl@0
   139
{
sl@0
   140
  GList *list;
sl@0
   141
  GSequenceIter *iter;
sl@0
   142
  int i;
sl@0
   143
  
sl@0
   144
  g_sequence_check (info->sequence);
sl@0
   145
  
sl@0
   146
  if (g_sequence_get_length (info->sequence) != info->n_items)
sl@0
   147
    g_print ("%d %d\n",
sl@0
   148
	     g_sequence_get_length (info->sequence), info->n_items);
sl@0
   149
  g_assert (info->n_items == g_queue_get_length (info->queue));
sl@0
   150
  g_assert (g_sequence_get_length (info->sequence) == info->n_items);
sl@0
   151
sl@0
   152
  iter = g_sequence_get_begin_iter (info->sequence);
sl@0
   153
  list = info->queue->head;
sl@0
   154
  i = 0;
sl@0
   155
  while (iter != g_sequence_get_end_iter (info->sequence))
sl@0
   156
    {
sl@0
   157
      Item *item;
sl@0
   158
      g_assert (list->data == iter);
sl@0
   159
      item = get_item (list->data);
sl@0
   160
      g_assert (item->seq == info);
sl@0
   161
      
sl@0
   162
      iter = g_sequence_iter_next (iter);
sl@0
   163
      list = list->next;
sl@0
   164
      i++;
sl@0
   165
    }
sl@0
   166
  
sl@0
   167
  g_assert (info->n_items == g_queue_get_length (info->queue));
sl@0
   168
  g_assert (g_sequence_get_length (info->sequence) == info->n_items);
sl@0
   169
}
sl@0
   170
sl@0
   171
static gpointer
sl@0
   172
new_item (SequenceInfo *seq)
sl@0
   173
{
sl@0
   174
  Item *item = g_new (Item, 1);
sl@0
   175
  seq->n_items++;
sl@0
   176
  item->seq = seq;
sl@0
   177
  item->number = g_random_int ();
sl@0
   178
  
sl@0
   179
  /* There have been bugs in the past where the GSequence would
sl@0
   180
   * dereference the user pointers. This will make sure such
sl@0
   181
   * behavior causes crashes
sl@0
   182
   */
sl@0
   183
  return ((char *)item + 1);
sl@0
   184
}
sl@0
   185
sl@0
   186
static void
sl@0
   187
free_item (gpointer data)
sl@0
   188
{
sl@0
   189
  Item *item = fix_pointer (data);
sl@0
   190
  item->seq->n_items--;
sl@0
   191
  g_free (item);
sl@0
   192
}
sl@0
   193
sl@0
   194
static void
sl@0
   195
seq_foreach (gpointer data,
sl@0
   196
	     gpointer user_data)
sl@0
   197
{
sl@0
   198
  Item *item = fix_pointer (data);
sl@0
   199
  GList **link = user_data;
sl@0
   200
  GSequenceIter *iter;
sl@0
   201
  
sl@0
   202
  g_assert (*link != NULL);
sl@0
   203
  
sl@0
   204
  iter = (*link)->data;
sl@0
   205
  
sl@0
   206
  g_assert (get_item (iter) == item);
sl@0
   207
  
sl@0
   208
  item->number = g_random_int();
sl@0
   209
  
sl@0
   210
  *link = (*link)->next;
sl@0
   211
}
sl@0
   212
sl@0
   213
static gint
sl@0
   214
compare_items (gconstpointer a,
sl@0
   215
	       gconstpointer b,
sl@0
   216
	       gpointer	     data)
sl@0
   217
{
sl@0
   218
  const Item *item_a = fix_pointer (a);
sl@0
   219
  const Item *item_b = fix_pointer (b);
sl@0
   220
sl@0
   221
  if (item_a->number < item_b->number)
sl@0
   222
    {
sl@0
   223
      return -1;
sl@0
   224
    }
sl@0
   225
  else if (item_a->number == item_b->number)
sl@0
   226
    {
sl@0
   227
      /* Force an arbitrary order on the items
sl@0
   228
       * We have to do this, since g_queue_insert_sorted() and
sl@0
   229
       * g_sequence_insert_sorted() do not agree on the exact
sl@0
   230
       * position the item is inserted if the new item is
sl@0
   231
       * equal to an existing one.
sl@0
   232
       */
sl@0
   233
      if (item_a < item_b)
sl@0
   234
	return -1;
sl@0
   235
      else if (item_a == item_b)
sl@0
   236
	return 0;
sl@0
   237
      else
sl@0
   238
	return 1;
sl@0
   239
    }
sl@0
   240
  else
sl@0
   241
    {
sl@0
   242
      return 1;
sl@0
   243
    }
sl@0
   244
}
sl@0
   245
sl@0
   246
static void
sl@0
   247
check_sorted (SequenceInfo *info)
sl@0
   248
{
sl@0
   249
  GList *list;
sl@0
   250
  int last;
sl@0
   251
  GSequenceIter *last_iter;
sl@0
   252
  
sl@0
   253
  check_integrity (info);
sl@0
   254
  
sl@0
   255
  last = G_MININT;
sl@0
   256
  last_iter = NULL;
sl@0
   257
  for (list = info->queue->head; list != NULL; list = list->next)
sl@0
   258
    {
sl@0
   259
      GSequenceIter *iter = list->data;
sl@0
   260
      Item *item = get_item (iter);
sl@0
   261
      
sl@0
   262
      g_assert (item->number >= last);
sl@0
   263
      /* Check that the ordering is the same as that of the queue,
sl@0
   264
       * ie. that the sort is stable
sl@0
   265
       */
sl@0
   266
      if (last_iter)
sl@0
   267
	g_assert (iter == g_sequence_iter_next (last_iter));
sl@0
   268
      
sl@0
   269
      last = item->number;
sl@0
   270
      last_iter = iter;
sl@0
   271
    }
sl@0
   272
}
sl@0
   273
sl@0
   274
static gint
sl@0
   275
compare_iters (gconstpointer a,
sl@0
   276
	       gconstpointer b,
sl@0
   277
	       gpointer      data)
sl@0
   278
{
sl@0
   279
  GSequence *seq = data;
sl@0
   280
  GSequenceIter *iter_a = (GSequenceIter *)a;
sl@0
   281
  GSequenceIter *iter_b = (GSequenceIter *)b;
sl@0
   282
  /* compare_items() will fix up the pointers */
sl@0
   283
  Item *item_a = g_sequence_get (iter_a);
sl@0
   284
  Item *item_b = g_sequence_get (iter_b);
sl@0
   285
  
sl@0
   286
  if (seq)
sl@0
   287
    {
sl@0
   288
      g_assert (g_sequence_iter_get_sequence (iter_a) == seq);
sl@0
   289
      g_assert (g_sequence_iter_get_sequence (iter_b) == seq);
sl@0
   290
    }
sl@0
   291
  
sl@0
   292
  return compare_items (item_a, item_b, data);
sl@0
   293
}
sl@0
   294
sl@0
   295
/* A version of g_queue_link_index() that treats NULL as just
sl@0
   296
 * beyond the queue
sl@0
   297
 */
sl@0
   298
static int
sl@0
   299
queue_link_index (SequenceInfo *seq, GList *link)
sl@0
   300
{
sl@0
   301
  if (link)
sl@0
   302
    return g_queue_link_index (seq->queue, link);
sl@0
   303
  else
sl@0
   304
    return g_queue_get_length (seq->queue);
sl@0
   305
}
sl@0
   306
sl@0
   307
static void
sl@0
   308
get_random_range (SequenceInfo *seq,
sl@0
   309
		  GSequenceIter **begin_iter,
sl@0
   310
		  GSequenceIter **end_iter,
sl@0
   311
		  GList **begin_link,
sl@0
   312
		  GList **end_link)
sl@0
   313
{
sl@0
   314
  int length = g_queue_get_length (seq->queue);
sl@0
   315
  int b = g_random_int_range (0, length + 1);
sl@0
   316
  int e = g_random_int_range (b, length + 1);
sl@0
   317
  
sl@0
   318
  g_assert (length == g_sequence_get_length (seq->sequence));
sl@0
   319
  
sl@0
   320
  if (begin_iter)
sl@0
   321
    *begin_iter = g_sequence_get_iter_at_pos (seq->sequence, b);
sl@0
   322
  if (end_iter)
sl@0
   323
    *end_iter = g_sequence_get_iter_at_pos (seq->sequence, e);
sl@0
   324
  if (begin_link)
sl@0
   325
    *begin_link = g_queue_peek_nth_link (seq->queue, b);
sl@0
   326
  if (end_link)
sl@0
   327
    *end_link = g_queue_peek_nth_link (seq->queue, e);
sl@0
   328
  if (begin_iter && begin_link)
sl@0
   329
    {
sl@0
   330
      g_assert (
sl@0
   331
		queue_link_index (seq, *begin_link) ==
sl@0
   332
		g_sequence_iter_get_position (*begin_iter));
sl@0
   333
    }
sl@0
   334
  if (end_iter && end_link)
sl@0
   335
    {
sl@0
   336
      g_assert (
sl@0
   337
		queue_link_index (seq, *end_link) ==
sl@0
   338
		g_sequence_iter_get_position (*end_iter));
sl@0
   339
    }
sl@0
   340
}
sl@0
   341
sl@0
   342
static gint
sl@0
   343
get_random_position (SequenceInfo *seq)
sl@0
   344
{
sl@0
   345
  int length = g_queue_get_length (seq->queue);
sl@0
   346
  
sl@0
   347
  g_assert (length == g_sequence_get_length (seq->sequence));
sl@0
   348
  
sl@0
   349
  return g_random_int_range (-2, length + 5);
sl@0
   350
}
sl@0
   351
sl@0
   352
static GSequenceIter *
sl@0
   353
get_random_iter (SequenceInfo  *seq,
sl@0
   354
		 GList        **link)
sl@0
   355
{
sl@0
   356
  GSequenceIter *iter;
sl@0
   357
  int pos = get_random_position (seq);
sl@0
   358
  if (link)
sl@0
   359
    *link = g_queue_peek_nth_link (seq->queue, pos);
sl@0
   360
  iter = g_sequence_get_iter_at_pos (seq->sequence, pos);
sl@0
   361
  if (link)
sl@0
   362
    g_assert (queue_link_index (seq, *link) == g_sequence_iter_get_position (iter));
sl@0
   363
  return iter;
sl@0
   364
}
sl@0
   365
sl@0
   366
static void
sl@0
   367
dump_info (SequenceInfo *seq)
sl@0
   368
{
sl@0
   369
#if 0
sl@0
   370
  GSequenceIter *iter;
sl@0
   371
  GList *list;
sl@0
   372
  
sl@0
   373
  iter = g_sequence_get_begin_iter (seq->sequence);
sl@0
   374
  list = seq->queue->head;
sl@0
   375
  
sl@0
   376
  while (iter != g_sequence_get_end_iter (seq->sequence))
sl@0
   377
    {
sl@0
   378
      Item *item = get_item (iter);
sl@0
   379
      g_print ("%p  %p    %d\n", list->data, iter, item->number);
sl@0
   380
      
sl@0
   381
      iter = g_sequence_iter_next (iter);
sl@0
   382
      list = list->next;
sl@0
   383
    }
sl@0
   384
#endif
sl@0
   385
}
sl@0
   386
sl@0
   387
/* A version of g_queue_insert_before() that appends if link is NULL */
sl@0
   388
static void
sl@0
   389
queue_insert_before (SequenceInfo *seq, GList *link, gpointer data)
sl@0
   390
{
sl@0
   391
  if (link)
sl@0
   392
    g_queue_insert_before (seq->queue, link, data);
sl@0
   393
  else
sl@0
   394
    g_queue_push_tail (seq->queue, data);
sl@0
   395
}
sl@0
   396
sl@0
   397
static void
sl@0
   398
run_random_tests (guint32 seed)
sl@0
   399
{
sl@0
   400
#ifndef __SYMBIAN32__
sl@0
   401
#define N_ITERATIONS 60000
sl@0
   402
#else
sl@0
   403
#define N_ITERATIONS 600
sl@0
   404
#endif//__SYMBIAN32__    
sl@0
   405
#define N_SEQUENCES 8
sl@0
   406
#define N_TIMES 24
sl@0
   407
    
sl@0
   408
  SequenceInfo sequences[N_SEQUENCES];
sl@0
   409
  int k;
sl@0
   410
  
sl@0
   411
  g_print ("    seed: %u\n", seed);
sl@0
   412
  
sl@0
   413
  g_random_set_seed (seed);
sl@0
   414
  
sl@0
   415
  for (k = 0; k < N_SEQUENCES; ++k)
sl@0
   416
    {
sl@0
   417
      sequences[k].queue = g_queue_new ();
sl@0
   418
      sequences[k].sequence = g_sequence_new (free_item);
sl@0
   419
      sequences[k].n_items = 0;
sl@0
   420
    }
sl@0
   421
  
sl@0
   422
#define RANDOM_SEQUENCE() &(sequences[g_random_int_range (0, N_SEQUENCES)])
sl@0
   423
  
sl@0
   424
  for (k = 0; k < N_ITERATIONS; ++k)
sl@0
   425
    {
sl@0
   426
      int i;
sl@0
   427
      SequenceInfo *seq = RANDOM_SEQUENCE();
sl@0
   428
      int op = g_random_int_range (0, N_OPS);
sl@0
   429
sl@0
   430
#if 0
sl@0
   431
      g_print ("%d on %p\n", op, seq);
sl@0
   432
#endif
sl@0
   433
      
sl@0
   434
      switch (op)
sl@0
   435
	{
sl@0
   436
	case NEW:
sl@0
   437
	case FREE:
sl@0
   438
	  {
sl@0
   439
	    g_queue_free (seq->queue);
sl@0
   440
	    g_sequence_free (seq->sequence);
sl@0
   441
	    
sl@0
   442
	    g_assert (seq->n_items == 0);
sl@0
   443
	    
sl@0
   444
	    seq->queue = g_queue_new ();
sl@0
   445
	    seq->sequence = g_sequence_new (free_item);
sl@0
   446
	    
sl@0
   447
	    check_integrity (seq);
sl@0
   448
	  }
sl@0
   449
	  break;
sl@0
   450
	case GET_LENGTH:
sl@0
   451
	  {
sl@0
   452
	    int slen = g_sequence_get_length (seq->sequence);
sl@0
   453
	    int qlen = g_queue_get_length (seq->queue);
sl@0
   454
	    
sl@0
   455
	    g_assert (slen == qlen);
sl@0
   456
	  }
sl@0
   457
	  break;
sl@0
   458
	case FOREACH:
sl@0
   459
	  {
sl@0
   460
	    GList *link = seq->queue->head;
sl@0
   461
	    g_sequence_foreach (seq->sequence, seq_foreach, &link);
sl@0
   462
	    g_assert (link == NULL);
sl@0
   463
	  }
sl@0
   464
	  break;
sl@0
   465
	case FOREACH_RANGE:
sl@0
   466
	  {
sl@0
   467
	    GSequenceIter *begin_iter, *end_iter;
sl@0
   468
	    GList *begin_link, *end_link;
sl@0
   469
	    
sl@0
   470
	    get_random_range (seq, &begin_iter, &end_iter, &begin_link, &end_link);
sl@0
   471
	    
sl@0
   472
	    check_integrity (seq);
sl@0
   473
	    
sl@0
   474
	    g_sequence_foreach_range (begin_iter, end_iter, seq_foreach, &begin_link);
sl@0
   475
	    
sl@0
   476
	    g_assert (begin_link == end_link);
sl@0
   477
	  }
sl@0
   478
	  break;
sl@0
   479
	case SORT:
sl@0
   480
	  {
sl@0
   481
	    dump_info (seq);
sl@0
   482
	    
sl@0
   483
	    g_sequence_sort (seq->sequence, compare_items, NULL);
sl@0
   484
	    g_queue_sort (seq->queue, compare_iters, NULL);
sl@0
   485
	    
sl@0
   486
	    check_sorted (seq);
sl@0
   487
	    
sl@0
   488
	    dump_info (seq);
sl@0
   489
	  }
sl@0
   490
	  break;
sl@0
   491
	case SORT_ITER:
sl@0
   492
	  {
sl@0
   493
	    check_integrity (seq);
sl@0
   494
	    g_sequence_sort_iter (seq->sequence,
sl@0
   495
				  (GSequenceIterCompareFunc)compare_iters, seq->sequence);
sl@0
   496
	    g_queue_sort (seq->queue, compare_iters, NULL);
sl@0
   497
	    check_sorted (seq);
sl@0
   498
	  }
sl@0
   499
	  break;
sl@0
   500
	  
sl@0
   501
	  /* Getting iters */
sl@0
   502
	case GET_END_ITER:
sl@0
   503
	case GET_BEGIN_ITER:
sl@0
   504
	  {
sl@0
   505
	    GSequenceIter *begin_iter;
sl@0
   506
	    GSequenceIter *end_iter;
sl@0
   507
	    GSequenceIter *penultimate_iter;
sl@0
   508
	    
sl@0
   509
	    begin_iter = g_sequence_get_begin_iter (seq->sequence);
sl@0
   510
	    check_integrity (seq);
sl@0
   511
	    
sl@0
   512
	    end_iter = g_sequence_get_end_iter (seq->sequence);
sl@0
   513
	    check_integrity (seq);
sl@0
   514
	    
sl@0
   515
	    penultimate_iter = g_sequence_iter_prev (end_iter);
sl@0
   516
	    check_integrity (seq);
sl@0
   517
	    
sl@0
   518
	    if (g_sequence_get_length (seq->sequence) > 0)
sl@0
   519
	      {
sl@0
   520
		g_assert (seq->queue->head);
sl@0
   521
		g_assert (seq->queue->head->data == begin_iter);
sl@0
   522
		g_assert (seq->queue->tail);
sl@0
   523
		g_assert (seq->queue->tail->data == penultimate_iter);
sl@0
   524
	      }
sl@0
   525
	    else
sl@0
   526
	      {
sl@0
   527
		g_assert (penultimate_iter == end_iter);
sl@0
   528
		g_assert (begin_iter == end_iter);
sl@0
   529
		g_assert (penultimate_iter == begin_iter);
sl@0
   530
		g_assert (seq->queue->head == NULL);
sl@0
   531
		g_assert (seq->queue->tail == NULL);
sl@0
   532
	      }
sl@0
   533
	  }
sl@0
   534
	  break;
sl@0
   535
	case GET_ITER_AT_POS:
sl@0
   536
	  {
sl@0
   537
	    int i;
sl@0
   538
	    
sl@0
   539
	    g_assert (g_queue_get_length (seq->queue) == g_sequence_get_length (seq->sequence));
sl@0
   540
	    
sl@0
   541
	    for (i = 0; i < 10; ++i)
sl@0
   542
	      {
sl@0
   543
		int pos = get_random_position (seq);
sl@0
   544
		GSequenceIter *iter = g_sequence_get_iter_at_pos (seq->sequence, pos);
sl@0
   545
		GList *link = g_queue_peek_nth_link (seq->queue, pos);
sl@0
   546
		check_integrity (seq);
sl@0
   547
		if (pos >= g_sequence_get_length (seq->sequence) || pos < 0)
sl@0
   548
		  {
sl@0
   549
		    g_assert (iter == g_sequence_get_end_iter (seq->sequence));
sl@0
   550
		    g_assert (link == NULL);
sl@0
   551
		  }
sl@0
   552
		else
sl@0
   553
		  {
sl@0
   554
		    g_assert (link);
sl@0
   555
		    g_assert (link->data == iter);
sl@0
   556
		  }
sl@0
   557
	      }
sl@0
   558
	  }
sl@0
   559
	  break;
sl@0
   560
	case APPEND:
sl@0
   561
	  {
sl@0
   562
	    for (i = 0; i < 10; ++i)
sl@0
   563
	      {
sl@0
   564
		GSequenceIter *iter = g_sequence_append (seq->sequence, new_item (seq));
sl@0
   565
		g_queue_push_tail (seq->queue, iter);
sl@0
   566
	      }
sl@0
   567
	  }
sl@0
   568
	  break;
sl@0
   569
	case PREPEND:
sl@0
   570
	  {
sl@0
   571
	    for (i = 0; i < 10; ++i)
sl@0
   572
	      {
sl@0
   573
		GSequenceIter *iter = g_sequence_prepend (seq->sequence, new_item (seq));
sl@0
   574
		g_queue_push_head (seq->queue, iter);
sl@0
   575
	      }
sl@0
   576
	  }
sl@0
   577
	  break;
sl@0
   578
	case INSERT_BEFORE:
sl@0
   579
	  {
sl@0
   580
	    for (i = 0; i < 10; ++i)
sl@0
   581
	      {
sl@0
   582
		GList *link;
sl@0
   583
		GSequenceIter *iter = get_random_iter (seq, &link);
sl@0
   584
		GSequenceIter *new_iter;
sl@0
   585
		check_integrity (seq);
sl@0
   586
		
sl@0
   587
		new_iter = g_sequence_insert_before (iter, new_item (seq));
sl@0
   588
		
sl@0
   589
		queue_insert_before (seq, link, new_iter);
sl@0
   590
	      }
sl@0
   591
	  }
sl@0
   592
	  break;
sl@0
   593
 	case MOVE:
sl@0
   594
	  {
sl@0
   595
	    GList *link1, *link2;
sl@0
   596
	    SequenceInfo *seq1 = RANDOM_SEQUENCE();
sl@0
   597
	    SequenceInfo *seq2 = RANDOM_SEQUENCE();
sl@0
   598
	    GSequenceIter *iter1 = get_random_iter (seq1, &link1);
sl@0
   599
	    GSequenceIter *iter2 = get_random_iter (seq2, &link2);
sl@0
   600
	    
sl@0
   601
	    if (!g_sequence_iter_is_end (iter1))
sl@0
   602
	      {
sl@0
   603
		g_sequence_move (iter1, iter2);
sl@0
   604
		
sl@0
   605
		if (!link2)
sl@0
   606
		  g_assert (g_sequence_iter_is_end (iter2));
sl@0
   607
		
sl@0
   608
		queue_insert_before (seq2, link2, link1->data);
sl@0
   609
		
sl@0
   610
		g_queue_delete_link (seq1->queue, link1);
sl@0
   611
sl@0
   612
		get_item (iter1)->seq = seq2;
sl@0
   613
		
sl@0
   614
		seq1->n_items--;
sl@0
   615
		seq2->n_items++;
sl@0
   616
	      }
sl@0
   617
	    
sl@0
   618
	    check_integrity (seq);
sl@0
   619
	    
sl@0
   620
	    iter1 = get_random_iter (seq, NULL);
sl@0
   621
	    
sl@0
   622
	    /* Moving an iter to itself should have no effect */
sl@0
   623
	    if (!g_sequence_iter_is_end (iter1))
sl@0
   624
	      g_sequence_move (iter1, iter1);
sl@0
   625
	  }
sl@0
   626
	  break;
sl@0
   627
	case SWAP:
sl@0
   628
	  {
sl@0
   629
	    GList *link1, *link2;
sl@0
   630
	    SequenceInfo *seq1 = RANDOM_SEQUENCE();
sl@0
   631
	    SequenceInfo *seq2 = RANDOM_SEQUENCE();
sl@0
   632
	    GSequenceIter *iter1 = get_random_iter (seq1, &link1);
sl@0
   633
	    GSequenceIter *iter2 = get_random_iter (seq2, &link2);
sl@0
   634
	    
sl@0
   635
	    if (!g_sequence_iter_is_end (iter1) &&
sl@0
   636
		!g_sequence_iter_is_end (iter2))
sl@0
   637
	      {
sl@0
   638
		gpointer tmp;
sl@0
   639
sl@0
   640
		g_sequence_swap (iter1, iter2);
sl@0
   641
sl@0
   642
		get_item (iter1)->seq = seq2;
sl@0
   643
		get_item (iter2)->seq = seq1;
sl@0
   644
		
sl@0
   645
		tmp = link1->data;
sl@0
   646
		link1->data = link2->data;
sl@0
   647
		link2->data = tmp;
sl@0
   648
	      }
sl@0
   649
	  }
sl@0
   650
	  break;
sl@0
   651
	case INSERT_SORTED:
sl@0
   652
	  {
sl@0
   653
	    int i;
sl@0
   654
	    dump_info (seq);
sl@0
   655
	    
sl@0
   656
	    g_sequence_sort (seq->sequence, compare_items, NULL);
sl@0
   657
	    g_queue_sort (seq->queue, compare_iters, NULL);
sl@0
   658
	    
sl@0
   659
	    check_sorted (seq);
sl@0
   660
	    
sl@0
   661
	    for (i = 0; i < N_TIMES; ++i)
sl@0
   662
	      {
sl@0
   663
		GSequenceIter *iter =
sl@0
   664
		  g_sequence_insert_sorted (seq->sequence, new_item(seq), compare_items, NULL);
sl@0
   665
		
sl@0
   666
		g_queue_insert_sorted (seq->queue, iter, compare_iters, NULL);
sl@0
   667
	      }
sl@0
   668
	    
sl@0
   669
	    check_sorted (seq);
sl@0
   670
	    
sl@0
   671
	    dump_info (seq);
sl@0
   672
	  }
sl@0
   673
	  break;
sl@0
   674
	case INSERT_SORTED_ITER:
sl@0
   675
	  {
sl@0
   676
	    int i;
sl@0
   677
	    dump_info (seq);
sl@0
   678
	    
sl@0
   679
	    g_sequence_sort (seq->sequence, compare_items, NULL);
sl@0
   680
	    g_queue_sort (seq->queue, compare_iters, NULL);
sl@0
   681
	    
sl@0
   682
	    check_sorted (seq);
sl@0
   683
	    
sl@0
   684
	    for (i = 0; i < N_TIMES; ++i)
sl@0
   685
	      {
sl@0
   686
		GSequenceIter *iter;
sl@0
   687
sl@0
   688
		iter = g_sequence_insert_sorted_iter (seq->sequence,
sl@0
   689
						      new_item (seq),
sl@0
   690
						      (GSequenceIterCompareFunc)compare_iters,
sl@0
   691
						      seq->sequence);
sl@0
   692
		
sl@0
   693
		g_queue_insert_sorted (seq->queue, iter, compare_iters, NULL);
sl@0
   694
	      }
sl@0
   695
	    
sl@0
   696
	    check_sorted (seq);
sl@0
   697
	    
sl@0
   698
	    dump_info (seq);
sl@0
   699
	  }
sl@0
   700
	  break;
sl@0
   701
	case SORT_CHANGED:
sl@0
   702
	  {
sl@0
   703
	    int i;
sl@0
   704
	    
sl@0
   705
	    g_sequence_sort (seq->sequence, compare_items, NULL);
sl@0
   706
	    g_queue_sort (seq->queue, compare_iters, NULL);
sl@0
   707
	    
sl@0
   708
	    check_sorted (seq);
sl@0
   709
	    
sl@0
   710
	    for (i = 0; i < N_TIMES; ++i)
sl@0
   711
	      {
sl@0
   712
		GList *link;
sl@0
   713
		GSequenceIter *iter = get_random_iter (seq, &link);
sl@0
   714
		
sl@0
   715
		if (!g_sequence_iter_is_end (iter))
sl@0
   716
		  {
sl@0
   717
		    g_sequence_set (iter, new_item (seq));
sl@0
   718
		    g_sequence_sort_changed (iter, compare_items, NULL);
sl@0
   719
		    
sl@0
   720
		    g_queue_delete_link (seq->queue, link);
sl@0
   721
		    g_queue_insert_sorted (seq->queue, iter, compare_iters, NULL);
sl@0
   722
		  }
sl@0
   723
		
sl@0
   724
		check_sorted (seq);
sl@0
   725
	      }
sl@0
   726
	  }
sl@0
   727
	  break;
sl@0
   728
	case SORT_CHANGED_ITER:
sl@0
   729
	  {
sl@0
   730
	    int i;
sl@0
   731
	    
sl@0
   732
	    g_sequence_sort (seq->sequence, compare_items, NULL);
sl@0
   733
	    g_queue_sort (seq->queue, compare_iters, NULL);
sl@0
   734
	    
sl@0
   735
	    check_sorted (seq);
sl@0
   736
	    
sl@0
   737
	    for (i = 0; i < N_TIMES; ++i)
sl@0
   738
	      {
sl@0
   739
		GList *link;
sl@0
   740
		GSequenceIter *iter = get_random_iter (seq, &link);
sl@0
   741
		
sl@0
   742
		if (!g_sequence_iter_is_end (iter))
sl@0
   743
		  {
sl@0
   744
		    g_sequence_set (iter, new_item (seq));
sl@0
   745
		    g_sequence_sort_changed_iter (iter,
sl@0
   746
						  (GSequenceIterCompareFunc)compare_iters, seq->sequence);
sl@0
   747
		    
sl@0
   748
		    g_queue_delete_link (seq->queue, link);
sl@0
   749
		    g_queue_insert_sorted (seq->queue, iter, compare_iters, NULL);
sl@0
   750
		  }
sl@0
   751
		
sl@0
   752
		check_sorted (seq);
sl@0
   753
	      }
sl@0
   754
	  }
sl@0
   755
	  break;
sl@0
   756
	case REMOVE:
sl@0
   757
	  {
sl@0
   758
	    int i;
sl@0
   759
	    
sl@0
   760
	    for (i = 0; i < N_TIMES; ++i)
sl@0
   761
	      {
sl@0
   762
		GList *link;
sl@0
   763
		GSequenceIter *iter = get_random_iter (seq, &link);
sl@0
   764
		
sl@0
   765
		if (!g_sequence_iter_is_end (iter))
sl@0
   766
		  {
sl@0
   767
		    g_sequence_remove (iter);
sl@0
   768
		    g_queue_delete_link (seq->queue, link);
sl@0
   769
		  }
sl@0
   770
	      }
sl@0
   771
	  }
sl@0
   772
	  break;
sl@0
   773
	case REMOVE_RANGE:
sl@0
   774
	  {
sl@0
   775
	    GSequenceIter *begin_iter, *end_iter;
sl@0
   776
	    GList *begin_link, *end_link;
sl@0
   777
	    GList *list;
sl@0
   778
	    
sl@0
   779
	    get_random_range (seq, &begin_iter, &end_iter, &begin_link, &end_link);
sl@0
   780
	    
sl@0
   781
	    g_sequence_remove_range (begin_iter, end_iter);
sl@0
   782
	    
sl@0
   783
	    list = begin_link;
sl@0
   784
	    while (list != end_link)
sl@0
   785
	      {
sl@0
   786
		GList *next = list->next;
sl@0
   787
		
sl@0
   788
		g_queue_delete_link (seq->queue, list);
sl@0
   789
		
sl@0
   790
		list = next;
sl@0
   791
	      }
sl@0
   792
	  }
sl@0
   793
	  break;
sl@0
   794
	case MOVE_RANGE:
sl@0
   795
	  {
sl@0
   796
	    SequenceInfo *src = RANDOM_SEQUENCE();
sl@0
   797
	    SequenceInfo *dst = RANDOM_SEQUENCE();
sl@0
   798
	    
sl@0
   799
	    GSequenceIter *begin_iter, *end_iter;
sl@0
   800
	    GList *begin_link, *end_link;
sl@0
   801
	    
sl@0
   802
	    GSequenceIter *dst_iter;
sl@0
   803
	    GList *dst_link;
sl@0
   804
	    
sl@0
   805
	    GList *list;
sl@0
   806
	    
sl@0
   807
	    g_assert (src->queue);
sl@0
   808
	    g_assert (dst->queue);
sl@0
   809
	    
sl@0
   810
	    get_random_range (src, &begin_iter, &end_iter, &begin_link, &end_link);
sl@0
   811
	    dst_iter = get_random_iter (dst, &dst_link);
sl@0
   812
	    
sl@0
   813
	    g_sequence_move_range (dst_iter, begin_iter, end_iter);
sl@0
   814
	    
sl@0
   815
	    if (dst_link == begin_link || (src == dst && dst_link == end_link))
sl@0
   816
	      {
sl@0
   817
		check_integrity (src);
sl@0
   818
		check_integrity (dst);
sl@0
   819
		break;
sl@0
   820
	      }
sl@0
   821
	    
sl@0
   822
	    if (queue_link_index (src, begin_link) >=
sl@0
   823
		queue_link_index (src, end_link))
sl@0
   824
	      {
sl@0
   825
		break;
sl@0
   826
	      }
sl@0
   827
	    
sl@0
   828
	    if (src == dst &&
sl@0
   829
		queue_link_index (src, dst_link) >= queue_link_index (src, begin_link) &&
sl@0
   830
		queue_link_index (src, dst_link) <= queue_link_index (src, end_link))
sl@0
   831
	      {
sl@0
   832
		break;
sl@0
   833
	      }
sl@0
   834
	    
sl@0
   835
	    list = begin_link;
sl@0
   836
	    while (list != end_link)
sl@0
   837
	      {
sl@0
   838
		GList *next = list->next;
sl@0
   839
		Item *item = get_item (list->data);
sl@0
   840
		
sl@0
   841
		g_assert (dst->queue);
sl@0
   842
		queue_insert_before (dst, dst_link, list->data);
sl@0
   843
		g_queue_delete_link (src->queue, list);
sl@0
   844
		
sl@0
   845
		g_assert (item->seq == src);
sl@0
   846
		
sl@0
   847
		src->n_items--;
sl@0
   848
		dst->n_items++;
sl@0
   849
		item->seq = dst;
sl@0
   850
		
sl@0
   851
		list = next;
sl@0
   852
	      }
sl@0
   853
	  }
sl@0
   854
	  break;
sl@0
   855
	case SEARCH:
sl@0
   856
	  {
sl@0
   857
	    Item *item;
sl@0
   858
	    GSequenceIter *search_iter;
sl@0
   859
	    GSequenceIter *insert_iter;
sl@0
   860
	    
sl@0
   861
	    g_sequence_sort (seq->sequence, compare_items, NULL);
sl@0
   862
	    g_queue_sort (seq->queue, compare_iters, NULL);
sl@0
   863
	    
sl@0
   864
	    check_sorted (seq);
sl@0
   865
	    
sl@0
   866
	    item = new_item (seq);
sl@0
   867
	    search_iter = g_sequence_search (seq->sequence, item, compare_items, NULL);
sl@0
   868
	    
sl@0
   869
	    insert_iter = g_sequence_insert_sorted (seq->sequence, item, compare_items, NULL);
sl@0
   870
	    
sl@0
   871
	    g_assert (search_iter == g_sequence_iter_next (insert_iter));
sl@0
   872
	    
sl@0
   873
	    g_queue_insert_sorted (seq->queue, insert_iter, compare_iters, NULL);
sl@0
   874
	  }
sl@0
   875
	  break;
sl@0
   876
	case SEARCH_ITER:
sl@0
   877
	  {
sl@0
   878
	    Item *item;
sl@0
   879
	    GSequenceIter *search_iter;
sl@0
   880
	    GSequenceIter *insert_iter;
sl@0
   881
	    
sl@0
   882
	    g_sequence_sort (seq->sequence, compare_items, NULL);
sl@0
   883
	    g_queue_sort (seq->queue, compare_iters, NULL);
sl@0
   884
	    
sl@0
   885
	    check_sorted (seq);
sl@0
   886
	    
sl@0
   887
	    item = new_item (seq);
sl@0
   888
	    search_iter = g_sequence_search_iter (seq->sequence,
sl@0
   889
						  item,
sl@0
   890
						  (GSequenceIterCompareFunc)compare_iters, seq->sequence);
sl@0
   891
	    
sl@0
   892
	    insert_iter = g_sequence_insert_sorted (seq->sequence, item, compare_items, NULL);
sl@0
   893
	    
sl@0
   894
	    g_assert (search_iter == g_sequence_iter_next (insert_iter));
sl@0
   895
	    
sl@0
   896
	    g_queue_insert_sorted (seq->queue, insert_iter, compare_iters, NULL);
sl@0
   897
	  }
sl@0
   898
	  break;
sl@0
   899
	  
sl@0
   900
	  /* dereferencing */
sl@0
   901
	case GET:
sl@0
   902
	case SET:
sl@0
   903
	  {
sl@0
   904
	    GSequenceIter *iter;
sl@0
   905
	    GList *link;
sl@0
   906
	    
sl@0
   907
	    iter = get_random_iter (seq, &link);
sl@0
   908
	    
sl@0
   909
	    if (!g_sequence_iter_is_end (iter))
sl@0
   910
	      {
sl@0
   911
		Item *item;
sl@0
   912
		int i;
sl@0
   913
		
sl@0
   914
		check_integrity (seq);
sl@0
   915
		
sl@0
   916
		/* Test basic functionality */
sl@0
   917
		item = new_item (seq);
sl@0
   918
		g_sequence_set (iter, item);
sl@0
   919
		g_assert (g_sequence_get (iter) == item);
sl@0
   920
		
sl@0
   921
		/* Make sure that existing items are freed */
sl@0
   922
		for (i = 0; i < N_TIMES; ++i)
sl@0
   923
		  g_sequence_set (iter, new_item (seq));
sl@0
   924
		
sl@0
   925
		check_integrity (seq);
sl@0
   926
		
sl@0
   927
		g_sequence_set (iter, new_item (seq));
sl@0
   928
	      }
sl@0
   929
	  }
sl@0
   930
	  break;
sl@0
   931
	  
sl@0
   932
	  /* operations on GSequenceIter * */
sl@0
   933
	case ITER_IS_BEGIN:
sl@0
   934
	  {
sl@0
   935
	    GSequenceIter *iter;
sl@0
   936
	    
sl@0
   937
	    iter = g_sequence_get_iter_at_pos (seq->sequence, 0);
sl@0
   938
	    
sl@0
   939
	    g_assert (g_sequence_iter_is_begin (iter));
sl@0
   940
	    
sl@0
   941
	    check_integrity (seq);
sl@0
   942
	    
sl@0
   943
	    if (g_sequence_get_length (seq->sequence) > 0)
sl@0
   944
	      {
sl@0
   945
		g_assert (!g_sequence_iter_is_begin (g_sequence_get_end_iter (seq->sequence)));
sl@0
   946
	      }
sl@0
   947
	    else
sl@0
   948
	      {
sl@0
   949
		g_assert (g_sequence_iter_is_begin (g_sequence_get_end_iter (seq->sequence)));
sl@0
   950
	      }
sl@0
   951
	    
sl@0
   952
	    g_assert (g_sequence_iter_is_begin (g_sequence_get_begin_iter (seq->sequence)));
sl@0
   953
	  }
sl@0
   954
	  break;
sl@0
   955
	case ITER_IS_END:
sl@0
   956
	  {
sl@0
   957
	    GSequenceIter *iter;
sl@0
   958
	    int len = g_sequence_get_length (seq->sequence);
sl@0
   959
	    
sl@0
   960
	    iter = g_sequence_get_iter_at_pos (seq->sequence, len);
sl@0
   961
	    
sl@0
   962
	    g_assert (g_sequence_iter_is_end (iter));
sl@0
   963
	    
sl@0
   964
	    if (len > 0)
sl@0
   965
	      {
sl@0
   966
		g_assert (!g_sequence_iter_is_end (g_sequence_get_begin_iter (seq->sequence)));
sl@0
   967
	      }
sl@0
   968
	    else
sl@0
   969
	      {
sl@0
   970
		g_assert (g_sequence_iter_is_end (g_sequence_get_begin_iter (seq->sequence)));
sl@0
   971
	      }
sl@0
   972
	    
sl@0
   973
	    g_assert (g_sequence_iter_is_end (g_sequence_get_end_iter (seq->sequence)));
sl@0
   974
	  }
sl@0
   975
	  break;
sl@0
   976
	case ITER_NEXT:
sl@0
   977
	  {
sl@0
   978
	    GSequenceIter *iter1, *iter2, *iter3, *end;
sl@0
   979
	    
sl@0
   980
	    iter1 = g_sequence_append (seq->sequence, new_item (seq));
sl@0
   981
	    iter2 = g_sequence_append (seq->sequence, new_item (seq));
sl@0
   982
	    iter3 = g_sequence_append (seq->sequence, new_item (seq));
sl@0
   983
	    
sl@0
   984
	    end = g_sequence_get_end_iter (seq->sequence);
sl@0
   985
	    
sl@0
   986
	    g_assert (g_sequence_iter_next (iter1) == iter2);
sl@0
   987
	    g_assert (g_sequence_iter_next (iter2) == iter3);
sl@0
   988
	    g_assert (g_sequence_iter_next (iter3) == end);
sl@0
   989
	    g_assert (g_sequence_iter_next (end) == end);
sl@0
   990
	    
sl@0
   991
	    g_queue_push_tail (seq->queue, iter1);
sl@0
   992
	    g_queue_push_tail (seq->queue, iter2);
sl@0
   993
	    g_queue_push_tail (seq->queue, iter3);
sl@0
   994
	  }
sl@0
   995
	  break;
sl@0
   996
	case ITER_PREV:
sl@0
   997
	  {
sl@0
   998
	    GSequenceIter *iter1, *iter2, *iter3, *begin;
sl@0
   999
	    
sl@0
  1000
	    iter1 = g_sequence_prepend (seq->sequence, new_item (seq));
sl@0
  1001
	    iter2 = g_sequence_prepend (seq->sequence, new_item (seq));
sl@0
  1002
	    iter3 = g_sequence_prepend (seq->sequence, new_item (seq));
sl@0
  1003
	    
sl@0
  1004
	    begin = g_sequence_get_begin_iter (seq->sequence);
sl@0
  1005
	    
sl@0
  1006
	    g_assert (g_sequence_iter_prev (iter1) == iter2);
sl@0
  1007
	    g_assert (g_sequence_iter_prev (iter2) == iter3);
sl@0
  1008
	    g_assert (iter3 == begin);
sl@0
  1009
	    g_assert (g_sequence_iter_prev (iter3) == begin);
sl@0
  1010
	    g_assert (g_sequence_iter_prev (begin) == begin);
sl@0
  1011
	    
sl@0
  1012
	    g_queue_push_head (seq->queue, iter1);
sl@0
  1013
	    g_queue_push_head (seq->queue, iter2);
sl@0
  1014
	    g_queue_push_head (seq->queue, iter3);
sl@0
  1015
	  }
sl@0
  1016
	  break;
sl@0
  1017
	case ITER_GET_POSITION:
sl@0
  1018
	  {
sl@0
  1019
	    GList *link;
sl@0
  1020
	    GSequenceIter *iter = get_random_iter (seq, &link);
sl@0
  1021
	    
sl@0
  1022
	    g_assert (g_sequence_iter_get_position (iter) ==
sl@0
  1023
		      queue_link_index (seq, link));
sl@0
  1024
	  }
sl@0
  1025
	  break;
sl@0
  1026
	case ITER_MOVE:
sl@0
  1027
	  {
sl@0
  1028
	    int len = g_sequence_get_length (seq->sequence);
sl@0
  1029
	    GSequenceIter *iter;
sl@0
  1030
	    int pos;
sl@0
  1031
	    
sl@0
  1032
	    iter = get_random_iter (seq, NULL);
sl@0
  1033
	    pos = g_sequence_iter_get_position (iter);
sl@0
  1034
	    iter = g_sequence_iter_move (iter, len - pos);
sl@0
  1035
	    g_assert (g_sequence_iter_is_end (iter));
sl@0
  1036
	    
sl@0
  1037
	    
sl@0
  1038
	    iter = get_random_iter (seq, NULL);
sl@0
  1039
	    pos = g_sequence_iter_get_position (iter);
sl@0
  1040
	    while (pos < len)
sl@0
  1041
	      {
sl@0
  1042
		g_assert (!g_sequence_iter_is_end (iter));
sl@0
  1043
		pos++;
sl@0
  1044
		iter = g_sequence_iter_move (iter, 1);
sl@0
  1045
	      }
sl@0
  1046
	    g_assert (g_sequence_iter_is_end (iter));
sl@0
  1047
	  }
sl@0
  1048
	  break;
sl@0
  1049
	case ITER_GET_SEQUENCE:
sl@0
  1050
	  {
sl@0
  1051
	    GSequenceIter *iter = get_random_iter (seq, NULL);
sl@0
  1052
	    
sl@0
  1053
	    g_assert (g_sequence_iter_get_sequence (iter) == seq->sequence);
sl@0
  1054
	  }
sl@0
  1055
	  break;
sl@0
  1056
	  
sl@0
  1057
	  /* search */
sl@0
  1058
	case ITER_COMPARE:
sl@0
  1059
	  {
sl@0
  1060
	    GList *link1, *link2;
sl@0
  1061
	    GSequenceIter *iter1 = get_random_iter (seq, &link1);
sl@0
  1062
	    GSequenceIter *iter2 = get_random_iter (seq, &link2);
sl@0
  1063
	    
sl@0
  1064
	    int cmp = g_sequence_iter_compare (iter1, iter2);
sl@0
  1065
	    int pos1 = queue_link_index (seq, link1);
sl@0
  1066
	    int pos2 = queue_link_index (seq, link2);
sl@0
  1067
	    
sl@0
  1068
	    if (cmp == 0)
sl@0
  1069
	      {
sl@0
  1070
		g_assert (pos1 == pos2);
sl@0
  1071
	      }
sl@0
  1072
	    else if (cmp < 0)
sl@0
  1073
	      {
sl@0
  1074
		g_assert (pos1 < pos2);
sl@0
  1075
	      }
sl@0
  1076
	    else
sl@0
  1077
	      {
sl@0
  1078
		g_assert (pos1 > pos2);
sl@0
  1079
	      }
sl@0
  1080
	  }
sl@0
  1081
	  break;
sl@0
  1082
	case RANGE_GET_MIDPOINT:
sl@0
  1083
	  {
sl@0
  1084
	    GSequenceIter *iter1 = get_random_iter (seq, NULL);
sl@0
  1085
	    GSequenceIter *iter2 = get_random_iter (seq, NULL);
sl@0
  1086
	    GSequenceIter *iter3;
sl@0
  1087
	    int cmp;
sl@0
  1088
	    
sl@0
  1089
	    cmp = g_sequence_iter_compare (iter1, iter2);
sl@0
  1090
	    
sl@0
  1091
	    if (cmp > 0)
sl@0
  1092
	      {
sl@0
  1093
		GSequenceIter *tmp;
sl@0
  1094
		
sl@0
  1095
		tmp = iter1;
sl@0
  1096
		iter1 = iter2;
sl@0
  1097
		iter2 = tmp;
sl@0
  1098
	      }
sl@0
  1099
	    
sl@0
  1100
	    iter3 = g_sequence_range_get_midpoint (iter1, iter2);
sl@0
  1101
	    
sl@0
  1102
	    if (cmp == 0)
sl@0
  1103
	      {
sl@0
  1104
		g_assert (iter3 == iter1);
sl@0
  1105
		g_assert (iter3 == iter2);
sl@0
  1106
	      }
sl@0
  1107
	    
sl@0
  1108
	    g_assert (g_sequence_iter_get_position (iter3) >= 
sl@0
  1109
		      g_sequence_iter_get_position (iter1));
sl@0
  1110
	    g_assert (g_sequence_iter_get_position (iter2) >= 
sl@0
  1111
		      g_sequence_iter_get_position (iter3));
sl@0
  1112
	  }
sl@0
  1113
	  break;
sl@0
  1114
	  
sl@0
  1115
	}
sl@0
  1116
      
sl@0
  1117
      check_integrity (seq);
sl@0
  1118
    }
sl@0
  1119
}
sl@0
  1120
sl@0
  1121
/* Random seeds known to have failed at one point
sl@0
  1122
 */
sl@0
  1123
static gulong seeds[] =
sl@0
  1124
  {
sl@0
  1125
    825541564u,
sl@0
  1126
    801678400u,
sl@0
  1127
    1477639090u,
sl@0
  1128
    3369132895u,
sl@0
  1129
    1192944867u,
sl@0
  1130
    770458294u,
sl@0
  1131
    1099575817u,
sl@0
  1132
    590523467u,
sl@0
  1133
    3583571454u,
sl@0
  1134
    579241222u
sl@0
  1135
  };
sl@0
  1136
sl@0
  1137
static void standalone_tests (void);
sl@0
  1138
sl@0
  1139
static guint32
sl@0
  1140
get_seed (int argc, char **argv)
sl@0
  1141
{
sl@0
  1142
  if (argc > 1)
sl@0
  1143
    {
sl@0
  1144
      char *endptr;
sl@0
  1145
      
sl@0
  1146
      return strtol (argv[1], &endptr, 0);
sl@0
  1147
    }
sl@0
  1148
  else
sl@0
  1149
    {
sl@0
  1150
      return g_random_int();
sl@0
  1151
    }
sl@0
  1152
}
sl@0
  1153
sl@0
  1154
int
sl@0
  1155
main (int argc,
sl@0
  1156
      char **argv)
sl@0
  1157
{
sl@0
  1158
  guint32 seed = get_seed (argc, argv);
sl@0
  1159
  int i;
sl@0
  1160
 #ifdef __SYMBIAN32__
sl@0
  1161
  g_log_set_handler (NULL,  G_LOG_FLAG_FATAL| G_LOG_FLAG_RECURSION | G_LOG_LEVEL_CRITICAL | G_LOG_LEVEL_WARNING | G_LOG_LEVEL_MESSAGE | G_LOG_LEVEL_INFO | G_LOG_LEVEL_DEBUG, &mrtLogHandler, NULL);
sl@0
  1162
  g_set_print_handler(mrtPrintHandler);
sl@0
  1163
  #endif /*__SYMBIAN32__*/ 
sl@0
  1164
  /* Run stand alone tests */
sl@0
  1165
  g_print ("running standalone tests\n");
sl@0
  1166
  standalone_tests();
sl@0
  1167
  
sl@0
  1168
  g_print ("running regression tests:\n");
sl@0
  1169
  /* Run regression tests */
sl@0
  1170
  for (i = 0; i < G_N_ELEMENTS (seeds); ++i)
sl@0
  1171
    {
sl@0
  1172
      run_random_tests (seeds[i]);
sl@0
  1173
    }
sl@0
  1174
  
sl@0
  1175
  /* Run with a new random seed */
sl@0
  1176
  g_print ("random seed:\n");
sl@0
  1177
  run_random_tests (seed);
sl@0
  1178
  
sl@0
  1179
 #if __SYMBIAN32__
sl@0
  1180
  testResultXml("sequence-test");
sl@0
  1181
  #endif /* EMULATOR */ 
sl@0
  1182
  return 0;
sl@0
  1183
}
sl@0
  1184
sl@0
  1185
sl@0
  1186
/* Single, stand-alone tests */
sl@0
  1187
sl@0
  1188
static void
sl@0
  1189
test_out_of_range_jump (void)
sl@0
  1190
{
sl@0
  1191
  GSequence *seq = g_sequence_new (NULL);
sl@0
  1192
  GSequenceIter *iter = g_sequence_get_begin_iter (seq);
sl@0
  1193
  
sl@0
  1194
  g_sequence_iter_move (iter, 5);
sl@0
  1195
  
sl@0
  1196
  g_assert (g_sequence_iter_is_begin (iter));
sl@0
  1197
  g_assert (g_sequence_iter_is_end (iter));
sl@0
  1198
}
sl@0
  1199
sl@0
  1200
static int
sl@0
  1201
compare (gconstpointer a, gconstpointer b, gpointer userdata)
sl@0
  1202
{
sl@0
  1203
  int ai, bi;
sl@0
  1204
  
sl@0
  1205
  ai = GPOINTER_TO_INT (a);
sl@0
  1206
  bi = GPOINTER_TO_INT (b);
sl@0
  1207
  
sl@0
  1208
  if (ai < bi)
sl@0
  1209
    return -1;
sl@0
  1210
  else if (ai > bi)
sl@0
  1211
    return 1;
sl@0
  1212
  else
sl@0
  1213
    return 0;
sl@0
  1214
}
sl@0
  1215
sl@0
  1216
static int
sl@0
  1217
compare_iter (GSequenceIter *a,
sl@0
  1218
	      GSequenceIter *b,
sl@0
  1219
	      gpointer data)
sl@0
  1220
{
sl@0
  1221
  return compare (g_sequence_get (a),
sl@0
  1222
		  g_sequence_get (b),
sl@0
  1223
		  data);
sl@0
  1224
}
sl@0
  1225
sl@0
  1226
static void
sl@0
  1227
test_insert_sorted_non_pointer (void)
sl@0
  1228
{
sl@0
  1229
  int i;
sl@0
  1230
  
sl@0
  1231
  for (i = 0; i < 10; i++)
sl@0
  1232
    {
sl@0
  1233
      GSequence *seq = g_sequence_new (NULL);
sl@0
  1234
      int j;
sl@0
  1235
      
sl@0
  1236
      for (j = 0; j < 10000; j++)
sl@0
  1237
	{
sl@0
  1238
	  g_sequence_insert_sorted (seq, GINT_TO_POINTER (g_random_int()),
sl@0
  1239
				    compare, NULL);
sl@0
  1240
	  
sl@0
  1241
	  g_sequence_insert_sorted_iter (seq, GINT_TO_POINTER (g_random_int()),
sl@0
  1242
					 compare_iter, NULL);
sl@0
  1243
	}
sl@0
  1244
sl@0
  1245
      g_sequence_check (seq);
sl@0
  1246
      
sl@0
  1247
      g_sequence_free (seq);
sl@0
  1248
    }
sl@0
  1249
}
sl@0
  1250
sl@0
  1251
static void
sl@0
  1252
test_stable_sort (void)
sl@0
  1253
{
sl@0
  1254
  int i;
sl@0
  1255
  GSequence *seq = g_sequence_new (NULL);
sl@0
  1256
  
sl@0
  1257
#define N_ITEMS 1000
sl@0
  1258
  
sl@0
  1259
  GSequenceIter *iters[N_ITEMS];
sl@0
  1260
  GSequenceIter *iter;
sl@0
  1261
  
sl@0
  1262
  for (i = 0; i < N_ITEMS; ++i)
sl@0
  1263
    {
sl@0
  1264
      iters[i] = g_sequence_append (seq, GINT_TO_POINTER (3000)); 
sl@0
  1265
      g_sequence_check (seq);
sl@0
  1266
      g_assert (g_sequence_iter_get_sequence (iters[i]) == seq);
sl@0
  1267
   }
sl@0
  1268
sl@0
  1269
  i = 0;
sl@0
  1270
  iter = g_sequence_get_begin_iter (seq);
sl@0
  1271
  g_assert (g_sequence_iter_get_sequence (iter) == seq);
sl@0
  1272
  g_sequence_check (seq);
sl@0
  1273
  while (!g_sequence_iter_is_end (iter))
sl@0
  1274
    {
sl@0
  1275
      g_assert (g_sequence_iter_get_sequence (iters[i]) == seq);
sl@0
  1276
      g_assert (iters[i++] == iter);
sl@0
  1277
      
sl@0
  1278
      iter = g_sequence_iter_next (iter);
sl@0
  1279
      g_sequence_check (seq);
sl@0
  1280
    }
sl@0
  1281
  
sl@0
  1282
  g_sequence_sort (seq, compare, NULL);
sl@0
  1283
  
sl@0
  1284
  i = 0;
sl@0
  1285
  iter = g_sequence_get_begin_iter (seq);
sl@0
  1286
  while (!g_sequence_iter_is_end (iter))
sl@0
  1287
    {
sl@0
  1288
      g_assert (g_sequence_iter_get_sequence (iters[i]) == seq);
sl@0
  1289
      g_assert (iters[i] == iter);
sl@0
  1290
      
sl@0
  1291
      iter = g_sequence_iter_next (iter);
sl@0
  1292
      g_sequence_check (seq);
sl@0
  1293
sl@0
  1294
      i++;
sl@0
  1295
    }
sl@0
  1296
  
sl@0
  1297
  for (i = N_ITEMS - 1; i >= 0; --i)
sl@0
  1298
    {
sl@0
  1299
      g_sequence_check (seq);
sl@0
  1300
      g_assert (g_sequence_iter_get_sequence (iters[i]) == seq);
sl@0
  1301
      g_assert (g_sequence_get_end_iter (seq) != iters[i]);
sl@0
  1302
      g_sequence_sort_changed (iters[i], compare, NULL);
sl@0
  1303
    }
sl@0
  1304
  
sl@0
  1305
  i = 0;
sl@0
  1306
  iter = g_sequence_get_begin_iter (seq);
sl@0
  1307
  while (!g_sequence_iter_is_end (iter))
sl@0
  1308
    {
sl@0
  1309
      g_assert (iters[i++] == iter);
sl@0
  1310
      
sl@0
  1311
      iter = g_sequence_iter_next (iter);
sl@0
  1312
      g_sequence_check (seq);
sl@0
  1313
    }
sl@0
  1314
}
sl@0
  1315
sl@0
  1316
static void
sl@0
  1317
standalone_tests (void)
sl@0
  1318
{
sl@0
  1319
  test_out_of_range_jump ();
sl@0
  1320
  test_insert_sorted_non_pointer ();
sl@0
  1321
  test_stable_sort ();
sl@0
  1322
}
sl@0
  1323