blob: 00af5cfc7cfad968a0a56e307a3f50e9a5973aed [file] [log] [blame]
// Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include <chromeos/test_helpers.h>
#include <chromeos/utility.h>
#include <limits>
#include <dbus/dbus.h>
#include <gtest/gtest.h>
#if BASE_VER >= 242728
#include <base/strings/string_number_conversions.h>
#else
#include <base/string_number_conversions.h>
#endif
#if BASE_VER >= 242728
using base::DictionaryValue;
using base::ListValue;
using base::Value;
#endif
static void MessageToValues(DBus::Message& m, std::vector<Value*>* result,
bool* success) {
Value* v = NULL;
*success = false;
ASSERT_TRUE(chromeos::DBusMessageToValue(m, &v));
ASSERT_TRUE(v != NULL);
ASSERT_EQ(Value::TYPE_LIST, v->GetType());
ListValue* lv = NULL;
ASSERT_TRUE(v->GetAsList(&lv));
std::vector<Value*> values;
for (size_t i = 0; i < lv->GetSize(); i++) {
Value* v0 = NULL;
ASSERT_TRUE(lv->Get(i, &v0));
values.push_back(v0);
}
*result = values;
*success = true;
}
static void MessageToOneValue(DBus::Message& m, Value** result,
bool* success) {
std::vector<Value*> values;
MessageToValues(m, &values, success);
ASSERT_EQ(1, values.size());
*result = values[0];
*success = true;
}
TEST(Utilities, DBusMessageToValueEmpty) {
DBus::CallMessage m;
std::vector<Value*> values;
bool ok = false;
MessageToValues(m, &values, &ok);
ASSERT_TRUE(ok);
EXPECT_EQ(0, values.size());
}
TEST(Utilities, DBusMessageToValueOnePrimitive) {
DBus::CallMessage m;
DBus::MessageIter iter = m.writer();
iter.append_bool(true);
Value* v = NULL;
bool ok = false;
MessageToOneValue(m, &v, &ok);
ASSERT_TRUE(ok);
EXPECT_EQ(Value::TYPE_BOOLEAN, v->GetType());
bool b;
EXPECT_TRUE(v->GetAsBoolean(&b));
EXPECT_TRUE(b);
}
TEST(Utilities, DBusMessageToValueMultiplePrimitives) {
DBus::CallMessage m;
DBus::MessageIter iter = m.writer();
int v0_old = -3;
int v1_old = 17;
iter.append_int32(v0_old);
iter.append_int32(v1_old);
std::vector<Value*> values;
bool ok = false;
MessageToValues(m, &values, &ok);
ASSERT_TRUE(ok);
ASSERT_EQ(2, values.size());
int v0_new;
EXPECT_TRUE(values[0]->GetAsInteger(&v0_new));
EXPECT_EQ(v0_old, v0_new);
int v1_new;
EXPECT_TRUE(values[1]->GetAsInteger(&v1_new));
EXPECT_EQ(v1_old, v1_new);
}
TEST(Utilities, DBusMessageToValueArray) {
DBus::CallMessage m;
DBus::MessageIter iter = m.writer();
DBus::MessageIter subiter = iter.new_array(DBUS_TYPE_INT32_AS_STRING);
int v0_old = 7;
int v1_old = -2;
subiter.append_int32(v0_old);
subiter.append_int32(v1_old);
iter.close_container(subiter);
Value* v = NULL;
bool ok = false;
MessageToOneValue(m, &v, &ok);
ASSERT_TRUE(ok);
ASSERT_EQ(Value::TYPE_LIST, v->GetType());
ListValue* lv = NULL;
ASSERT_TRUE(v->GetAsList(&lv));
ASSERT_TRUE(lv != NULL);
ASSERT_EQ(2, lv->GetSize());
Value* v0 = NULL;
ASSERT_TRUE(lv->Get(0, &v0));
ASSERT_TRUE(v0 != NULL);
int v0_new;
EXPECT_TRUE(v0->GetAsInteger(&v0_new));
EXPECT_EQ(v0_old, v0_new);
Value* v1 = NULL;
ASSERT_TRUE(lv->Get(1, &v1));
ASSERT_TRUE(v1 != NULL);
int v1_new;
EXPECT_TRUE(v1->GetAsInteger(&v1_new));
EXPECT_EQ(v1_old, v1_new);
}
TEST(Utilities, DBusMessageToValueDictionary) {
char entry_type[5] = {
DBUS_DICT_ENTRY_BEGIN_CHAR,
DBUS_TYPE_STRING,
DBUS_TYPE_INT32,
DBUS_DICT_ENTRY_END_CHAR,
'\0'
};
DBus::CallMessage m;
DBus::MessageIter iter = m.writer();
DBus::MessageIter subiter = iter.new_array(entry_type);
DBus::MessageIter subsubiter = subiter.new_dict_entry();
int foo_old = 17;
subsubiter.append_string("foo");
subsubiter.append_int32(foo_old);
subiter.close_container(subsubiter);
subsubiter = subiter.new_dict_entry();
int bar_old = 12;
subsubiter.append_string("bar");
subsubiter.append_int32(bar_old);
subiter.close_container(subsubiter);
iter.close_container(subiter);
Value* v = NULL;
bool ok = false;
MessageToOneValue(m, &v, &ok);
ASSERT_TRUE(ok);
ASSERT_EQ(Value::TYPE_DICTIONARY, v->GetType());
// TODO(ellyjones): There should be a GetAsDictionary() method on Value.
DictionaryValue* dv = static_cast<DictionaryValue*>(v);
int foo_new;
ASSERT_TRUE(dv->GetInteger("foo", &foo_new));
EXPECT_EQ(foo_old, foo_new);
int bar_new;
ASSERT_TRUE(dv->GetInteger("bar", &bar_new));
EXPECT_EQ(bar_old, bar_new);
}
TEST(Utilities, DBusMessageToValueIntTypes) {
DBus::CallMessage m;
DBus::MessageIter iter = m.writer();
uint32_t uint32_max_old = std::numeric_limits<uint32_t>::max();
iter.append_uint32(uint32_max_old);
int64_t int64_min_old = std::numeric_limits<int64_t>::min();
iter.append_int64(int64_min_old);
uint64_t uint64_max_old = std::numeric_limits<uint64_t>::max();
iter.append_uint64(uint64_max_old);
std::vector<Value*> values;
bool ok = false;
MessageToValues(m, &values, &ok);
ASSERT_TRUE(ok);
ASSERT_EQ(3, values.size());
std::string uint32_max_new;
std::string int64_min_new;
std::string uint64_max_new;
ASSERT_TRUE(values[0]->GetAsString(&uint32_max_new));
EXPECT_EQ(base::UintToString(uint32_max_old), uint32_max_new);
ASSERT_TRUE(values[1]->GetAsString(&int64_min_new));
EXPECT_EQ(base::Int64ToString(int64_min_old), int64_min_new);
ASSERT_TRUE(values[2]->GetAsString(&uint64_max_new));
EXPECT_EQ(base::Uint64ToString(uint64_max_old), uint64_max_new);
}