/* -*- mode: C; c-file-style: "gnu"; indent-tabs-mode: nil; -*- */
/* dbus-message-factory.c Generator of valid and invalid message data for test suite
 *
 * Copyright (C) 2005 Red Hat Inc.
 *
 * Licensed under the Academic Free License version 2.1
 * 
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 * 
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
 *
 */
#include <config.h>

#ifndef DOXYGEN_SHOULD_SKIP_THIS

#ifdef DBUS_ENABLE_EMBEDDED_TESTS
#include "dbus-message-factory.h"
#include "dbus-message-private.h"
#include "dbus-signature.h"
#include "dbus-test.h"
#include <stdio.h>

typedef enum
  {
    CHANGE_TYPE_ADJUST,
    CHANGE_TYPE_ABSOLUTE
  } ChangeType;

#define BYTE_ORDER_OFFSET  0
#define TYPE_OFFSET        1
#define BODY_LENGTH_OFFSET 4
#define FIELDS_ARRAY_LENGTH_OFFSET 12

static void
iter_recurse (DBusMessageDataIter *iter)
{
  iter->depth += 1;
  _dbus_assert (iter->depth < _DBUS_MESSAGE_DATA_MAX_NESTING);
  _dbus_assert (iter->sequence_nos[iter->depth] >= 0);
}

static int
iter_get_sequence (DBusMessageDataIter *iter)
{
  _dbus_assert (iter->sequence_nos[iter->depth] >= 0);
  return iter->sequence_nos[iter->depth];
}

static void
iter_set_sequence (DBusMessageDataIter *iter,
                   int                  sequence)
{
  _dbus_assert (sequence >= 0);
  iter->sequence_nos[iter->depth] = sequence;
}

static void
iter_unrecurse (DBusMessageDataIter *iter)
{
  iter->depth -= 1;
  _dbus_assert (iter->depth >= 0);
}

static void
iter_next (DBusMessageDataIter *iter)
{
  iter->sequence_nos[iter->depth] += 1;
}

static dbus_bool_t
iter_first_in_series (DBusMessageDataIter *iter)
{
  int i;

  i = iter->depth;
  while (i < _DBUS_MESSAGE_DATA_MAX_NESTING)
    {
      if (iter->sequence_nos[i] != 0)
        return FALSE;
      ++i;
    }
  return TRUE;
}

typedef dbus_bool_t (* DBusInnerGeneratorFunc)   (DBusMessageDataIter *iter,
                                                  DBusMessage        **message_p);
typedef dbus_bool_t (* DBusMessageGeneratorFunc) (DBusMessageDataIter *iter,
                                                  DBusString          *data,
                                                  DBusValidity        *expected_validity);

static void
set_reply_serial (DBusMessage *message)
{
  if (message == NULL)
    _dbus_assert_not_reached ("oom");
  if (!dbus_message_set_reply_serial (message, 100))
    _dbus_assert_not_reached ("oom");
}

static dbus_bool_t
generate_trivial_inner (DBusMessageDataIter *iter,
                        DBusMessage        **message_p)
{
  DBusMessage *message;

  switch (iter_get_sequence (iter))
    {
    case 0:
      message = dbus_message_new_method_call ("org.freedesktop.TextEditor",
                                              "/foo/bar",
                                              "org.freedesktop.DocumentFactory",
                                              "Create");
      break;
    case 1:
      message = dbus_message_new (DBUS_MESSAGE_TYPE_METHOD_RETURN);
      set_reply_serial (message);
      break;
    case 2:
      message = dbus_message_new_signal ("/foo/bar",
                                         "org.freedesktop.DocumentFactory",
                                         "Created");
      break;
    case 3:
      message = dbus_message_new (DBUS_MESSAGE_TYPE_ERROR);

      if (!dbus_message_set_error_name (message,
                                        "org.freedesktop.TestErrorName"))
        _dbus_assert_not_reached ("oom");
      
      {
        DBusMessageIter iter;
        const char *v_STRING = "This is an error";
        
        dbus_message_iter_init_append (message, &iter);
        if (!dbus_message_iter_append_basic (&iter,
                                             DBUS_TYPE_STRING,
                                             &v_STRING))
          _dbus_assert_not_reached ("oom");
      }
      
      set_reply_serial (message);
      break;
    default:
      return FALSE;
    }
  
  if (message == NULL)
    _dbus_assert_not_reached ("oom");

  *message_p = message;
  
  return TRUE;
}

static dbus_bool_t
generate_many_bodies_inner (DBusMessageDataIter *iter,
                            DBusMessage        **message_p)
{
  DBusMessage *message;
  DBusString signature;
  DBusString body;
  char byte_order;

  /* Keeping this small makes things go faster */
  message = dbus_message_new_method_call ("o.z.F",
                                          "/",
                                          "o.z.B",
                                          "Nah");
  if (message == NULL)
    _dbus_assert_not_reached ("oom");

  byte_order = _dbus_header_get_byte_order (&message->header);

  set_reply_serial (message);

  if (!_dbus_string_init (&signature) || !_dbus_string_init (&body))
    _dbus_assert_not_reached ("oom");
  
  if (dbus_internal_do_not_use_generate_bodies (iter_get_sequence (iter),
                                                byte_order,
                                                &signature, &body))
    {
      const char *v_SIGNATURE;

      v_SIGNATURE = _dbus_string_get_const_data (&signature);
      if (!_dbus_header_set_field_basic (&message->header,
                                         DBUS_HEADER_FIELD_SIGNATURE,
                                         DBUS_TYPE_SIGNATURE,
                                         &v_SIGNATURE))
        _dbus_assert_not_reached ("oom");

      if (!_dbus_string_move (&body, 0, &message->body, 0))
        _dbus_assert_not_reached ("oom");

      _dbus_marshal_set_uint32 (&message->header.data, BODY_LENGTH_OFFSET,
                                _dbus_string_get_length (&message->body),
                                byte_order);
      
      *message_p = message;
    }
  else
    {
      dbus_message_unref (message);
      *message_p = NULL;
    }
  
  _dbus_string_free (&signature);
  _dbus_string_free (&body);

  return *message_p != NULL;
}

static void
generate_from_message (DBusString            *data,
                       DBusValidity          *expected_validity,
                       DBusMessage           *message)
{
  dbus_message_set_serial (message, 1);
  dbus_message_lock (message);

  *expected_validity = DBUS_VALID;
  
  /* move for efficiency, since we'll nuke the message anyway */
  if (!_dbus_string_move (&message->header.data, 0,
                          data, 0))
    _dbus_assert_not_reached ("oom");

  if (!_dbus_string_copy (&message->body, 0,
                          data, _dbus_string_get_length (data)))
    _dbus_assert_not_reached ("oom");
}

static dbus_bool_t
generate_outer (DBusMessageDataIter   *iter,
                DBusString            *data,
                DBusValidity          *expected_validity,
                DBusInnerGeneratorFunc func)
{
  DBusMessage *message;

  message = NULL;
  if (!(*func)(iter, &message))
    return FALSE;

  iter_next (iter);
  
  _dbus_assert (message != NULL);

  generate_from_message (data, expected_validity, message);

  dbus_message_unref (message);

  return TRUE;
}

static dbus_bool_t
generate_trivial (DBusMessageDataIter   *iter,
                  DBusString            *data,
                  DBusValidity          *expected_validity)
{
  return generate_outer (iter, data, expected_validity,
                         generate_trivial_inner);
}

static dbus_bool_t
generate_many_bodies (DBusMessageDataIter   *iter,
                      DBusString            *data,
                      DBusValidity          *expected_validity)
{
  return generate_outer (iter, data, expected_validity,
                         generate_many_bodies_inner);
}

static DBusMessage*
simple_method_call (void)
{
  DBusMessage *message;
  /* Keeping this small makes stuff go faster */
  message = dbus_message_new_method_call ("o.b.Q",
                                          "/f/b",
                                          "o.b.Z",
                                          "Fro");
  if (message == NULL)
    _dbus_assert_not_reached ("oom");
  return message;
}

static DBusMessage*
simple_signal (void)
{
  DBusMessage *message;
  message = dbus_message_new_signal ("/f/b",
                                     "o.b.Z",
                                     "Fro");
  if (message == NULL)
    _dbus_assert_not_reached ("oom");
  return message;
}

static DBusMessage*
simple_method_return (void)
{
  DBusMessage *message;
  message =  dbus_message_new (DBUS_MESSAGE_TYPE_METHOD_RETURN);
  if (message == NULL)
    _dbus_assert_not_reached ("oom");

  set_reply_serial (message);
  
  return message;
}

static DBusMessage*
simple_error (void)
{
  DBusMessage *message;
  message =  dbus_message_new (DBUS_MESSAGE_TYPE_ERROR);
  if (message == NULL)
    _dbus_assert_not_reached ("oom");

  if (!dbus_message_set_error_name (message, "foo.bar"))
    _dbus_assert_not_reached ("oom");
  
  set_reply_serial (message);
  
  return message;
}

static DBusMessage*
message_with_nesting_levels (int levels)
{
  DBusMessage *message;
  dbus_int32_t v_INT32;
  DBusMessageIter *parents;
  DBusMessageIter *children;
  int i;

  /* If levels is higher it breaks sig_refcount in DBusMessageRealIter
   * in dbus-message.c, this assert is just to help you know you need
   * to fix that if you hit it
   */
  _dbus_assert (levels < 256);

  parents = dbus_new(DBusMessageIter, levels + 1);
  children = dbus_new(DBusMessageIter, levels + 1);

  v_INT32 = 42;
  message = simple_method_call ();

  i = 0;
  dbus_message_iter_init_append (message, &parents[i]);
  while (i < levels)
    {
      dbus_message_iter_open_container (&parents[i], DBUS_TYPE_VARIANT,
                                        i == (levels - 1) ?
                                        DBUS_TYPE_INT32_AS_STRING :
                                        DBUS_TYPE_VARIANT_AS_STRING,
                                        &children[i]);
      ++i;
      parents[i] = children[i-1];
    }
  --i;
  dbus_message_iter_append_basic (&children[i], DBUS_TYPE_INT32, &v_INT32);
  while (i >= 0)
    {
      dbus_message_iter_close_container (&parents[i], &children[i]);
      --i;
    }

  dbus_free(parents);
  dbus_free(children);

  return message;
}

static dbus_bool_t
generate_special (DBusMessageDataIter   *iter,
                  DBusString            *data,
                  DBusValidity          *expected_validity)
{
  int item_seq;
  DBusMessage *message;
  int pos;
  dbus_int32_t v_INT32;

  _dbus_assert (_dbus_string_get_length (data) == 0);
  
  message = NULL;
  pos = -1;
  v_INT32 = 42;
  item_seq = iter_get_sequence (iter);

  if (item_seq == 0)
    {
      message = simple_method_call ();
      if (!dbus_message_append_args (message,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INVALID))
        _dbus_assert_not_reached ("oom");
                                     
      _dbus_header_get_field_raw (&message->header,
                                  DBUS_HEADER_FIELD_SIGNATURE,
                                  NULL, &pos);
      generate_from_message (data, expected_validity, message);
      
      /* set an invalid typecode */
      _dbus_string_set_byte (data, pos + 1, '$');

      *expected_validity = DBUS_INVALID_UNKNOWN_TYPECODE;
    }
  else if (item_seq == 1)
    {
      char long_sig[DBUS_MAXIMUM_TYPE_RECURSION_DEPTH+2];
      const char *v_STRING;
      int i;
      
      message = simple_method_call ();
      if (!dbus_message_append_args (message,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INVALID))
        _dbus_assert_not_reached ("oom");

      i = 0;
      while (i < (DBUS_MAXIMUM_TYPE_RECURSION_DEPTH + 1))
        {
          long_sig[i] = DBUS_TYPE_ARRAY;
          ++i;
        }
      long_sig[i] = DBUS_TYPE_INVALID;

      v_STRING = long_sig;
      if (!_dbus_header_set_field_basic (&message->header,
                                         DBUS_HEADER_FIELD_SIGNATURE,
                                         DBUS_TYPE_SIGNATURE,
                                         &v_STRING))
        _dbus_assert_not_reached ("oom");
      
      _dbus_header_get_field_raw (&message->header,
                                  DBUS_HEADER_FIELD_SIGNATURE,
                                  NULL, &pos);
      generate_from_message (data, expected_validity, message);
      
      *expected_validity = DBUS_INVALID_EXCEEDED_MAXIMUM_ARRAY_RECURSION;
    }
  else if (item_seq == 2)
    {
      char long_sig[DBUS_MAXIMUM_TYPE_RECURSION_DEPTH*2+4];
      const char *v_STRING;
      int i;
      
      message = simple_method_call ();
      if (!dbus_message_append_args (message,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INVALID))
        _dbus_assert_not_reached ("oom");

      i = 0;
      while (i <= (DBUS_MAXIMUM_TYPE_RECURSION_DEPTH + 1))
        {
          long_sig[i] = DBUS_STRUCT_BEGIN_CHAR;
          ++i;
        }

      long_sig[i] = DBUS_TYPE_INT32;
      ++i;

      while (i < (DBUS_MAXIMUM_TYPE_RECURSION_DEPTH*2 + 3))
        {
          long_sig[i] = DBUS_STRUCT_END_CHAR;
          ++i;
        }
      long_sig[i] = DBUS_TYPE_INVALID;
      
      v_STRING = long_sig;
      if (!_dbus_header_set_field_basic (&message->header,
                                         DBUS_HEADER_FIELD_SIGNATURE,
                                         DBUS_TYPE_SIGNATURE,
                                         &v_STRING))
        _dbus_assert_not_reached ("oom");
      
      _dbus_header_get_field_raw (&message->header,
                                  DBUS_HEADER_FIELD_SIGNATURE,
                                  NULL, &pos);
      generate_from_message (data, expected_validity, message);
      
      *expected_validity = DBUS_INVALID_EXCEEDED_MAXIMUM_STRUCT_RECURSION;
    }
  else if (item_seq == 3)
    {
      message = simple_method_call ();
      if (!dbus_message_append_args (message,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INVALID))
        _dbus_assert_not_reached ("oom");
                                     
      _dbus_header_get_field_raw (&message->header,
                                  DBUS_HEADER_FIELD_SIGNATURE,
                                  NULL, &pos);
      generate_from_message (data, expected_validity, message);
      
      _dbus_string_set_byte (data, pos + 1, DBUS_STRUCT_BEGIN_CHAR);
      
      *expected_validity = DBUS_INVALID_STRUCT_STARTED_BUT_NOT_ENDED;
    }
  else if (item_seq == 4)
    {
      message = simple_method_call ();
      if (!dbus_message_append_args (message,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INVALID))
        _dbus_assert_not_reached ("oom");
                                     
      _dbus_header_get_field_raw (&message->header,
                                  DBUS_HEADER_FIELD_SIGNATURE,
                                  NULL, &pos);
      generate_from_message (data, expected_validity, message);
      
      _dbus_string_set_byte (data, pos + 1, DBUS_STRUCT_END_CHAR);
      
      *expected_validity = DBUS_INVALID_STRUCT_ENDED_BUT_NOT_STARTED;
    }
  else if (item_seq == 5)
    {
      message = simple_method_call ();
      if (!dbus_message_append_args (message,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INVALID))
        _dbus_assert_not_reached ("oom");
                                     
      _dbus_header_get_field_raw (&message->header,
                                  DBUS_HEADER_FIELD_SIGNATURE,
                                  NULL, &pos);
      generate_from_message (data, expected_validity, message);
      
      _dbus_string_set_byte (data, pos + 1, DBUS_STRUCT_BEGIN_CHAR);
      _dbus_string_set_byte (data, pos + 2, DBUS_STRUCT_END_CHAR);
      
      *expected_validity = DBUS_INVALID_STRUCT_HAS_NO_FIELDS;
    }
  else if (item_seq == 6)
    {
      message = simple_method_call ();
      generate_from_message (data, expected_validity, message);
      
      _dbus_string_set_byte (data, TYPE_OFFSET, DBUS_MESSAGE_TYPE_INVALID);
      
      *expected_validity = DBUS_INVALID_BAD_MESSAGE_TYPE;
    }
  else if (item_seq == 7)
    {
      /* Messages of unknown type are considered valid */
      message = simple_method_call ();
      generate_from_message (data, expected_validity, message);
      
      _dbus_string_set_byte (data, TYPE_OFFSET, 100);
      
      *expected_validity = DBUS_VALID;
    }
  else if (item_seq == 8)
    {
      char byte_order;

      message = simple_method_call ();
      byte_order = _dbus_header_get_byte_order (&message->header);
      generate_from_message (data, expected_validity, message);
      
      _dbus_marshal_set_uint32 (data, BODY_LENGTH_OFFSET,
                                DBUS_MAXIMUM_MESSAGE_LENGTH / 2 + 4,
                                byte_order);
      _dbus_marshal_set_uint32 (data, FIELDS_ARRAY_LENGTH_OFFSET,
                                DBUS_MAXIMUM_MESSAGE_LENGTH / 2 + 4,
                                byte_order);
      *expected_validity = DBUS_INVALID_MESSAGE_TOO_LONG;
    }
  else if (item_seq == 9)
    {
      const char *v_STRING = "not a valid bus name";
      message = simple_method_call ();

      if (!_dbus_header_set_field_basic (&message->header,
                                         DBUS_HEADER_FIELD_SENDER,
                                         DBUS_TYPE_STRING, &v_STRING))
        _dbus_assert_not_reached ("oom");
      
      generate_from_message (data, expected_validity, message);

      *expected_validity = DBUS_INVALID_BAD_SENDER;
    }
  else if (item_seq == 10)
    {
      message = simple_method_call ();

      if (!dbus_message_set_interface (message, DBUS_INTERFACE_LOCAL))
        _dbus_assert_not_reached ("oom");
      
      generate_from_message (data, expected_validity, message);

      *expected_validity = DBUS_INVALID_USES_LOCAL_INTERFACE;
    }
  else if (item_seq == 11)
    {
      message = simple_method_call ();

      if (!dbus_message_set_path (message, DBUS_PATH_LOCAL))
        _dbus_assert_not_reached ("oom");
      
      generate_from_message (data, expected_validity, message);

      *expected_validity = DBUS_INVALID_USES_LOCAL_PATH;
    }
  else if (item_seq == 12)
    {
      /* Method calls don't have to have interface */
      message = simple_method_call ();

      if (!dbus_message_set_interface (message, NULL))
        _dbus_assert_not_reached ("oom");
      
      generate_from_message (data, expected_validity, message);
      
      *expected_validity = DBUS_VALID;
    }
  else if (item_seq == 13)
    {
      /* Signals require an interface */
      message = simple_signal ();

      if (!dbus_message_set_interface (message, NULL))
        _dbus_assert_not_reached ("oom");
      
      generate_from_message (data, expected_validity, message);
      
      *expected_validity = DBUS_INVALID_MISSING_INTERFACE;
    }
  else if (item_seq == 14)
    {
      message = simple_method_return ();

      if (!_dbus_header_delete_field (&message->header, DBUS_HEADER_FIELD_REPLY_SERIAL))
        _dbus_assert_not_reached ("oom");
      
      generate_from_message (data, expected_validity, message);
      
      *expected_validity = DBUS_INVALID_MISSING_REPLY_SERIAL;
    }
  else if (item_seq == 15)
    {
      message = simple_error ();

      if (!dbus_message_set_error_name (message, NULL))
        _dbus_assert_not_reached ("oom");
      
      generate_from_message (data, expected_validity, message);
      
      *expected_validity = DBUS_INVALID_MISSING_ERROR_NAME;
    }
  else if (item_seq == 16)
    {
      char long_sig[DBUS_MAXIMUM_TYPE_RECURSION_DEPTH*4+10];
      const char *v_STRING;
      int i;
      int n_begins;
      
      message = simple_method_call ();
      if (!dbus_message_append_args (message,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INVALID))
        _dbus_assert_not_reached ("oom");

      i = 0;
      while (i <= (DBUS_MAXIMUM_TYPE_RECURSION_DEPTH*3 + 3))
        {
          long_sig[i] = DBUS_TYPE_ARRAY;
          ++i;
          long_sig[i] = DBUS_DICT_ENTRY_BEGIN_CHAR;
          ++i;
          long_sig[i] = DBUS_TYPE_INT32;
          ++i;
        }
      n_begins = i / 3;

      long_sig[i] = DBUS_TYPE_INT32;
      ++i;
      
      while (n_begins > 0)
        {
          long_sig[i] = DBUS_DICT_ENTRY_END_CHAR;
          ++i;
          n_begins -= 1;
        }
      long_sig[i] = DBUS_TYPE_INVALID;
      
      v_STRING = long_sig;
      if (!_dbus_header_set_field_basic (&message->header,
                                         DBUS_HEADER_FIELD_SIGNATURE,
                                         DBUS_TYPE_SIGNATURE,
                                         &v_STRING))
        _dbus_assert_not_reached ("oom");
      
      _dbus_header_get_field_raw (&message->header,
                                  DBUS_HEADER_FIELD_SIGNATURE,
                                  NULL, &pos);
      generate_from_message (data, expected_validity, message);
      
      *expected_validity = DBUS_INVALID_EXCEEDED_MAXIMUM_DICT_ENTRY_RECURSION;
    }
  else if (item_seq == 17)
    {
      message = simple_method_call ();
      if (!dbus_message_append_args (message,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INVALID))
        _dbus_assert_not_reached ("oom");
                                     
      _dbus_header_get_field_raw (&message->header,
                                  DBUS_HEADER_FIELD_SIGNATURE,
                                  NULL, &pos);
      generate_from_message (data, expected_validity, message);

      _dbus_string_set_byte (data, pos + 1, DBUS_TYPE_ARRAY);
      _dbus_string_set_byte (data, pos + 2, DBUS_DICT_ENTRY_BEGIN_CHAR);
      
      *expected_validity = DBUS_INVALID_DICT_ENTRY_STARTED_BUT_NOT_ENDED;
    }
  else if (item_seq == 18)
    {
      message = simple_method_call ();
      if (!dbus_message_append_args (message,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INVALID))
        _dbus_assert_not_reached ("oom");
                                     
      _dbus_header_get_field_raw (&message->header,
                                  DBUS_HEADER_FIELD_SIGNATURE,
                                  NULL, &pos);
      generate_from_message (data, expected_validity, message);
      
      _dbus_string_set_byte (data, pos + 1, DBUS_DICT_ENTRY_END_CHAR);
      
      *expected_validity = DBUS_INVALID_DICT_ENTRY_ENDED_BUT_NOT_STARTED;
    }
  else if (item_seq == 19)
    {
      message = simple_method_call ();
      if (!dbus_message_append_args (message,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INT32, &v_INT32,
                                     DBUS_TYPE_INVALID))
        _dbus_assert_not_reached ("oom");
                                     
      _dbus_header_get_field_raw (&message->header,
                                  DBUS_HEADER_FIELD_SIGNATURE,
                                  NULL, &pos);
      generate_from_message (data, expected_validity, message);

      _dbus_string_set_byte (data, pos + 1, DBUS_TYPE_ARRAY);
      _dbus_string_set_byte (data, pos + 2, DBUS_DICT_ENTRY_BEGIN_CHAR);
      _dbus_string_set_byte (data, pos + 3, DBUS_DICT_ENTRY_END_CHAR);
      
      *expected_validity = DBUS_INVALID_DICT_ENTRY_HAS_NO_FIELDS;
    }
  else if (item_seq == 20)
    {
      /* 64 levels of nesting is OK */
      message = message_with_nesting_levels(64);

      generate_from_message (data, expected_validity, message);

      *expected_validity = DBUS_VALID;
    }
  else if (item_seq == 21)
    {
      /* 65 levels of nesting is not OK */
      message = message_with_nesting_levels(65);

      generate_from_message (data, expected_validity, message);

      *expected_validity = DBUS_INVALID_NESTED_TOO_DEEPLY;
    }
  else
    {
      return FALSE;
    }

  if (message)
    dbus_message_unref (message);

  iter_next (iter);
  return TRUE;
}

static dbus_bool_t
generate_wrong_length (DBusMessageDataIter *iter,
                       DBusString          *data,
                       DBusValidity        *expected_validity)
{
  int lengths[] = { -42, -17, -16, -15, -9, -8, -7, -6, -5, -4, -3, -2, -1,
                    1, 2, 3, 4, 5, 6, 7, 8, 9, 15, 16, 30 };
  int adjust;
  int len_seq;

 restart:
  len_seq = iter_get_sequence (iter);
  if (len_seq == _DBUS_N_ELEMENTS (lengths))
    return FALSE;

  _dbus_assert (len_seq < _DBUS_N_ELEMENTS (lengths));
  
  iter_recurse (iter);
  if (!generate_many_bodies (iter, data, expected_validity))
    {
      iter_set_sequence (iter, 0); /* reset to first body */
      iter_unrecurse (iter);
      iter_next (iter);            /* next length adjustment */
      goto restart;
    }
  iter_unrecurse (iter);

  adjust = lengths[len_seq];

  if (adjust < 0)
    {
      if ((_dbus_string_get_length (data) + adjust) < DBUS_MINIMUM_HEADER_SIZE)
        _dbus_string_set_length (data, DBUS_MINIMUM_HEADER_SIZE);
      else
        _dbus_string_shorten (data, - adjust);
      *expected_validity = DBUS_INVALID_FOR_UNKNOWN_REASON;
    }
  else
    {      
      if (!_dbus_string_lengthen (data, adjust))
        _dbus_assert_not_reached ("oom");
      *expected_validity = DBUS_INVALID_TOO_MUCH_DATA;
    }

  /* Fixup lengths */
  {
    int old_body_len;
    int new_body_len;
    int byte_order;
    
    _dbus_assert (_dbus_string_get_length (data) >= DBUS_MINIMUM_HEADER_SIZE);
    
    byte_order = _dbus_string_get_byte (data, BYTE_ORDER_OFFSET);
    old_body_len = _dbus_marshal_read_uint32 (data,
                                              BODY_LENGTH_OFFSET,
                                              byte_order,
                                              NULL);
    _dbus_assert (old_body_len < _dbus_string_get_length (data));
    new_body_len = old_body_len + adjust;
    if (new_body_len < 0)
      {
        new_body_len = 0;
        /* we just munged the header, and aren't sure how */
        *expected_validity = DBUS_VALIDITY_UNKNOWN;
      }

    _dbus_verbose ("changing body len from %u to %u by adjust %d\n",
                   old_body_len, new_body_len, adjust);
    
    _dbus_marshal_set_uint32 (data, BODY_LENGTH_OFFSET,
                              new_body_len,
                              byte_order);
  }

  return TRUE;
}

static dbus_bool_t
generate_byte_changed (DBusMessageDataIter *iter,
                       DBusString          *data,
                       DBusValidity        *expected_validity)
{
  int byte_seq;
  int v_BYTE;

  /* This is a little convoluted to make the bodies the
   * outer loop and each byte of each body the inner
   * loop
   */

 restart:
  if (!generate_many_bodies (iter, data, expected_validity))
    return FALSE;

  iter_recurse (iter);
  byte_seq = iter_get_sequence (iter);
  iter_next (iter);
  iter_unrecurse (iter);
  
  if (byte_seq == _dbus_string_get_length (data))
    {
      _dbus_string_set_length (data, 0);
      /* reset byte count */
      iter_recurse (iter);
      iter_set_sequence (iter, 0);
      iter_unrecurse (iter);
      goto restart;
    }
  else
    {
      /* Undo the "next" in generate_many_bodies */
      iter_set_sequence (iter, iter_get_sequence (iter) - 1);
    }

  _dbus_assert (byte_seq < _dbus_string_get_length (data));
  v_BYTE = _dbus_string_get_byte (data, byte_seq);
  v_BYTE += byte_seq; /* arbitrary but deterministic change to the byte */
  _dbus_string_set_byte (data, byte_seq, v_BYTE);
  *expected_validity = DBUS_VALIDITY_UNKNOWN;

  return TRUE;
}

#if 0
/* This is really expensive and doesn't add too much coverage */

static dbus_bool_t
find_next_typecode (DBusMessageDataIter *iter,
                    DBusString          *data,
                    DBusValidity        *expected_validity)
{
  int body_seq;
  int byte_seq;
  int base_depth;

  base_depth = iter->depth;

 restart:
  _dbus_assert (iter->depth == (base_depth + 0));
  _dbus_string_set_length (data, 0);

  body_seq = iter_get_sequence (iter);
  
  if (!generate_many_bodies (iter, data, expected_validity))
    return FALSE;
  /* Undo the "next" in generate_many_bodies */
  iter_set_sequence (iter, body_seq);
  
  iter_recurse (iter);
  while (TRUE)
    {
      _dbus_assert (iter->depth == (base_depth + 1));
      
      byte_seq = iter_get_sequence (iter);

      _dbus_assert (byte_seq <= _dbus_string_get_length (data));
      
      if (byte_seq == _dbus_string_get_length (data))
        {
          /* reset byte count */
          iter_set_sequence (iter, 0);
          iter_unrecurse (iter);
          _dbus_assert (iter->depth == (base_depth + 0));
          iter_next (iter); /* go to the next body */
          goto restart;
        }

      _dbus_assert (byte_seq < _dbus_string_get_length (data));

      if (dbus_type_is_valid (_dbus_string_get_byte (data, byte_seq)))
        break;
      else
        iter_next (iter);
    }

  _dbus_assert (byte_seq == iter_get_sequence (iter));
  _dbus_assert (byte_seq < _dbus_string_get_length (data));

  iter_unrecurse (iter);

  _dbus_assert (iter->depth == (base_depth + 0));
  
  return TRUE;
}

static const int typecodes[] = {
  DBUS_TYPE_INVALID,
  DBUS_TYPE_BYTE,
  DBUS_TYPE_BOOLEAN,
  DBUS_TYPE_INT16,
  DBUS_TYPE_UINT16,
  DBUS_TYPE_INT32,
  DBUS_TYPE_UINT32,
  DBUS_TYPE_INT64,
  DBUS_TYPE_UINT64,
  DBUS_TYPE_DOUBLE,
  DBUS_TYPE_STRING,
  DBUS_TYPE_OBJECT_PATH,
  DBUS_TYPE_SIGNATURE,
  DBUS_TYPE_ARRAY,
  DBUS_TYPE_VARIANT,
  DBUS_STRUCT_BEGIN_CHAR,
  DBUS_STRUCT_END_CHAR,
  DBUS_DICT_ENTRY_BEGIN_CHAR,
  DBUS_DICT_ENTRY_END_CHAR,
  DBUS_TYPE_UNIX_FD,
  255 /* random invalid typecode */
};

static dbus_bool_t
generate_typecode_changed (DBusMessageDataIter *iter,
                           DBusString          *data,
                           DBusValidity        *expected_validity)
{
  int byte_seq;
  int typecode_seq;
  int base_depth;

  base_depth = iter->depth;

 restart:
  _dbus_assert (iter->depth == (base_depth + 0));
  _dbus_string_set_length (data, 0);
  
  if (!find_next_typecode (iter, data, expected_validity))
    return FALSE;

  iter_recurse (iter);
  byte_seq = iter_get_sequence (iter);

  _dbus_assert (byte_seq < _dbus_string_get_length (data));
  
  iter_recurse (iter);
  typecode_seq = iter_get_sequence (iter);
  iter_next (iter);

  _dbus_assert (typecode_seq <= _DBUS_N_ELEMENTS (typecodes));
  
  if (typecode_seq == _DBUS_N_ELEMENTS (typecodes))
    {
      _dbus_assert (iter->depth == (base_depth + 2));
      iter_set_sequence (iter, 0); /* reset typecode sequence */
      iter_unrecurse (iter);
      _dbus_assert (iter->depth == (base_depth + 1));
      iter_next (iter); /* go to the next byte_seq */
      iter_unrecurse (iter);
      _dbus_assert (iter->depth == (base_depth + 0));
      goto restart;
    }

  _dbus_assert (iter->depth == (base_depth + 2));
  iter_unrecurse (iter);
  _dbus_assert (iter->depth == (base_depth + 1));
  iter_unrecurse (iter);
  _dbus_assert (iter->depth == (base_depth + 0));

#if 0
  printf ("Changing byte %d in message %d to %c\n",
          byte_seq, iter_get_sequence (iter), typecodes[typecode_seq]);
#endif
  
  _dbus_string_set_byte (data, byte_seq, typecodes[typecode_seq]);
  *expected_validity = DBUS_VALIDITY_UNKNOWN;
  return TRUE;
}
#endif

typedef struct
{
  ChangeType type;
  dbus_uint32_t value; /* cast to signed for adjusts */
} UIntChange;

static const UIntChange uint32_changes[] = {
  { CHANGE_TYPE_ADJUST, (dbus_uint32_t) -1 },
  { CHANGE_TYPE_ADJUST, (dbus_uint32_t) -2 },
  { CHANGE_TYPE_ADJUST, (dbus_uint32_t) -3 },
  { CHANGE_TYPE_ADJUST, (dbus_uint32_t) 1 },
  { CHANGE_TYPE_ADJUST, (dbus_uint32_t) 2 },
  { CHANGE_TYPE_ADJUST, (dbus_uint32_t) 3 },
  { CHANGE_TYPE_ABSOLUTE, _DBUS_UINT32_MAX },
  { CHANGE_TYPE_ABSOLUTE, 0 },
  { CHANGE_TYPE_ABSOLUTE, 1 },
  { CHANGE_TYPE_ABSOLUTE, _DBUS_UINT32_MAX - 1 },
  { CHANGE_TYPE_ABSOLUTE, _DBUS_UINT32_MAX - 5 }
};

static dbus_bool_t
generate_uint32_changed (DBusMessageDataIter *iter,
                         DBusString          *data,
                         DBusValidity        *expected_validity)
{
  int body_seq;
  int byte_seq;
  int change_seq;
  dbus_uint32_t v_UINT32;
  int byte_order;
  const UIntChange *change;
  int base_depth;

  /* Outer loop is each body, next loop is each change,
   * inner loop is each change location
   */

  base_depth = iter->depth;
  
 next_body:
  _dbus_assert (iter->depth == (base_depth + 0));
  _dbus_string_set_length (data, 0);
  body_seq = iter_get_sequence (iter);
  
  if (!generate_many_bodies (iter, data, expected_validity))
    return FALSE;

  _dbus_assert (iter->depth == (base_depth + 0));

  iter_set_sequence (iter, body_seq); /* undo the "next" from generate_many_bodies */
  iter_recurse (iter);
 next_change:
  _dbus_assert (iter->depth == (base_depth + 1));
  change_seq = iter_get_sequence (iter);
  
  if (change_seq == _DBUS_N_ELEMENTS (uint32_changes))
    {
      /* Reset change count */
      iter_set_sequence (iter, 0);
      iter_unrecurse (iter);
      iter_next (iter);
      goto next_body;
    }

  _dbus_assert (iter->depth == (base_depth + 1));
  
  iter_recurse (iter);
  _dbus_assert (iter->depth == (base_depth + 2));
  byte_seq = iter_get_sequence (iter);
  /* skip 4 bytes at a time */
  iter_next (iter);
  iter_next (iter);
  iter_next (iter);
  iter_next (iter);
  iter_unrecurse (iter);

  _dbus_assert (_DBUS_ALIGN_VALUE (byte_seq, 4) == (unsigned) byte_seq);
  if (byte_seq >= (_dbus_string_get_length (data) - 4))
    {
      /* reset byte count */
      _dbus_assert (iter->depth == (base_depth + 1));
      iter_recurse (iter);
      _dbus_assert (iter->depth == (base_depth + 2));
      iter_set_sequence (iter, 0);
      iter_unrecurse (iter);
      _dbus_assert (iter->depth == (base_depth + 1));
      iter_next (iter);
      goto next_change;
    }
  
  _dbus_assert (byte_seq <= (_dbus_string_get_length (data) - 4));

  byte_order = _dbus_string_get_byte (data, BYTE_ORDER_OFFSET);
  
  v_UINT32 = _dbus_marshal_read_uint32 (data, byte_seq, byte_order, NULL);

  change = &uint32_changes[change_seq];

  if (change->type == CHANGE_TYPE_ADJUST)
    {
      v_UINT32 += (int) change->value;
    }
  else
    {
      v_UINT32 = change->value;
    }

#if 0
  printf ("body %d change %d pos %d ",
          body_seq, change_seq, byte_seq);

  if (change->type == CHANGE_TYPE_ADJUST)
    printf ("adjust by %d", (int) change->value);
  else
    printf ("set to %u", change->value);
  
  printf (" \t%u -> %u\n",
          _dbus_marshal_read_uint32 (data, byte_seq, byte_order, NULL),
          v_UINT32);
#endif
  
  _dbus_marshal_set_uint32 (data, byte_seq, v_UINT32, byte_order);
  *expected_validity = DBUS_VALIDITY_UNKNOWN;

  _dbus_assert (iter->depth == (base_depth + 1));
  iter_unrecurse (iter);
  _dbus_assert (iter->depth == (base_depth + 0));
          
  return TRUE;
}

typedef struct
{
  const char *name;
  DBusMessageGeneratorFunc func;  
} DBusMessageGenerator;

static const DBusMessageGenerator generators[] = {
  { "trivial example of each message type", generate_trivial },
  { "assorted arguments", generate_many_bodies },
  { "assorted special cases", generate_special },
  { "each uint32 modified", generate_uint32_changed },
  { "wrong body lengths", generate_wrong_length },
  { "each byte modified", generate_byte_changed },
#if 0
  /* This is really expensive and doesn't add too much coverage */
  { "change each typecode", generate_typecode_changed }
#endif
};

void
_dbus_message_data_free (DBusMessageData *data)
{
  _dbus_string_free (&data->data);
}

void
_dbus_message_data_iter_init (DBusMessageDataIter *iter)
{
  int i;
  
  iter->depth = 0;
  i = 0;
  while (i < _DBUS_MESSAGE_DATA_MAX_NESTING)
    {
      iter->sequence_nos[i] = 0;
      ++i;
    }
  iter->count = 0;
}

dbus_bool_t
_dbus_message_data_iter_get_and_next (DBusMessageDataIter *iter,
                                      DBusMessageData     *data)
{
  DBusMessageGeneratorFunc func;
  int generator;

 restart:
  generator = iter_get_sequence (iter);
  
  if (generator == _DBUS_N_ELEMENTS (generators))
    return FALSE;

  iter_recurse (iter);
  
  if (iter_first_in_series (iter))
    {
      printf (" testing message loading: %s ", generators[generator].name);
      fflush (stdout);
    }
  
  func = generators[generator].func;

  if (!_dbus_string_init (&data->data))
    _dbus_assert_not_reached ("oom");
  
  if ((*func)(iter, &data->data, &data->expected_validity))
    ;
  else
    {
      iter_set_sequence (iter, 0);
      iter_unrecurse (iter);
      iter_next (iter); /* next generator */
      _dbus_string_free (&data->data);
      printf ("%d test loads cumulative\n", iter->count);
      goto restart;
    }
  iter_unrecurse (iter);

  iter->count += 1;
  return TRUE;
}

#endif /* !DOXYGEN_SHOULD_SKIP_THIS */

#endif /* DBUS_ENABLE_EMBEDDED_TESTS */
