105 lines
3.2 KiB
C++
105 lines
3.2 KiB
C++
/*
|
|
Copyright (c) 2018 Microsoft Corporation. All rights reserved.
|
|
Released under Apache 2.0 license as described in the file LICENSE.
|
|
|
|
Author: Leonardo de Moura
|
|
*/
|
|
#include "util/kvmap.h"
|
|
|
|
namespace lean {
|
|
extern "C" object * lean_mk_bool_data_value(bool b);
|
|
extern "C" uint8 lean_data_value_bool(object * v);
|
|
extern "C" uint8 lean_data_value_beq(object * a, object * b);
|
|
|
|
data_value::data_value(bool v):
|
|
object_ref(lean_mk_bool_data_value(v)) {
|
|
}
|
|
|
|
bool data_value::get_bool() const {
|
|
lean_assert(kind() == data_value_kind::Bool);
|
|
return lean_data_value_bool(to_obj_arg());
|
|
}
|
|
|
|
bool operator==(data_value const & a, data_value const & b) {
|
|
if (a.raw() == b.raw()) return true;
|
|
return lean_data_value_beq(a.to_obj_arg(), b.to_obj_arg());
|
|
}
|
|
|
|
bool operator<(data_value const & a, data_value const & b) {
|
|
if (a.kind() != b.kind()) return static_cast<unsigned>(a.kind()) < static_cast<unsigned>(b.kind());
|
|
switch (a.kind()) {
|
|
case data_value_kind::String: return a.get_string() < b.get_string();
|
|
case data_value_kind::Nat: return a.get_nat() < b.get_nat();
|
|
case data_value_kind::Bool: return !a.get_bool() && b.get_bool();
|
|
case data_value_kind::Name: return a.get_name() < b.get_name();
|
|
}
|
|
/* TODO: compare Int and Syntax values */
|
|
return false;
|
|
}
|
|
|
|
optional<data_value> find(kvmap m, name const & k) {
|
|
while (!is_nil(m)) {
|
|
if (head(m).fst() == k)
|
|
return optional<data_value>(head(m).snd());
|
|
m = tail(m);
|
|
}
|
|
return optional<data_value>();
|
|
}
|
|
|
|
optional<string_ref> get_string(kvmap const & m, name const & k) {
|
|
optional<data_value> r = find(m, k);
|
|
if (r && r->kind() == data_value_kind::String)
|
|
return optional<string_ref>(r->get_string());
|
|
else
|
|
return optional<string_ref>();
|
|
}
|
|
|
|
optional<nat> get_nat(kvmap const & m, name const & k) {
|
|
optional<data_value> r = find(m, k);
|
|
if (r && r->kind() == data_value_kind::Nat)
|
|
return optional<nat>(r->get_nat());
|
|
else
|
|
return optional<nat>();
|
|
}
|
|
|
|
optional<bool> get_bool(kvmap const & m, name const & k) {
|
|
optional<data_value> r = find(m, k);
|
|
if (r && r->kind() == data_value_kind::Bool)
|
|
return optional<bool>(r->get_bool());
|
|
else
|
|
return optional<bool>();
|
|
}
|
|
|
|
optional<name> get_name(kvmap const & m, name const & k) {
|
|
optional<data_value> r = find(m, k);
|
|
if (r && r->kind() == data_value_kind::Name)
|
|
return optional<name>(r->get_name());
|
|
else
|
|
return optional<name>();
|
|
}
|
|
|
|
static kvmap insert(kvmap const & m, name const & k, data_value const & v) {
|
|
if (is_nil(m))
|
|
return kvmap(kvmap_entry(k, v));
|
|
else if (head(m).fst() == k)
|
|
return kvmap(kvmap_entry(k, v), tail(m));
|
|
else
|
|
return kvmap(head(m), insert(tail(m), k, v));
|
|
}
|
|
|
|
kvmap set_string(kvmap const & m, name const & k, string_ref const & v) {
|
|
return insert(m, k, data_value(v));
|
|
}
|
|
|
|
kvmap set_bool(kvmap const & m, name const & k, bool v) {
|
|
return insert(m, k, data_value(v));
|
|
}
|
|
|
|
kvmap set_name(kvmap const & m, name const & k, name const & v) {
|
|
return insert(m, k, data_value(v));
|
|
}
|
|
|
|
kvmap set_nat(kvmap const & m, name const & k, nat const & v) {
|
|
return insert(m, k, data_value(v));
|
|
}
|
|
}
|