feat(library/compiler/erase_irrelevant): convert enumeration types into uint* types
This commit is contained in:
parent
83ebacb8af
commit
8af0c85d4f
3 changed files with 34 additions and 8 deletions
|
|
@ -13,7 +13,7 @@ Author: Leonardo de Moura
|
|||
|
||||
namespace lean {
|
||||
class erase_irrelevant_fn {
|
||||
typedef std::unordered_map<name, bool, name_hash> is_enum_cache;
|
||||
typedef std::unordered_map<name, optional<expr>, name_hash> is_enum_cache;
|
||||
typedef std::tuple<name, expr, expr> let_entry;
|
||||
type_checker::state m_st;
|
||||
local_ctx m_lctx;
|
||||
|
|
@ -48,11 +48,14 @@ class erase_irrelevant_fn {
|
|||
}
|
||||
}
|
||||
|
||||
bool is_enum_type(name const & I) {
|
||||
optional<expr> is_enum_type(name const & I) {
|
||||
auto it = m_is_enum_cache.find(I);
|
||||
if (it != m_is_enum_cache.end())
|
||||
return it->second;
|
||||
bool r = static_cast<bool>(lean::is_enum_type(env(), I));
|
||||
optional<unsigned> nbytes = lean::is_enum_type(env(), I);
|
||||
if (!nbytes) return none_expr();
|
||||
optional<expr> r = to_uint_type(*nbytes);
|
||||
if (!r) return none_expr();
|
||||
m_is_enum_cache.insert(mk_pair(I, r));
|
||||
return r;
|
||||
}
|
||||
|
|
@ -95,8 +98,8 @@ class erase_irrelevant_fn {
|
|||
return e;
|
||||
else if (c == get_char_name())
|
||||
return mk_constant(get_uint32_name());
|
||||
else if (is_enum_type(c))
|
||||
return e;
|
||||
else if (optional<expr> uint = is_enum_type(c))
|
||||
return *uint;
|
||||
else
|
||||
return mk_enf_object_type();
|
||||
} else if (!atomic_only && is_app_of(e, get_array_name(), 1)) {
|
||||
|
|
|
|||
|
|
@ -40,6 +40,21 @@ optional<unsigned> is_enum_type(environment const & env, name const & I) {
|
|||
}
|
||||
}
|
||||
|
||||
static expr * g_uint8 = nullptr;
|
||||
static expr * g_uint16 = nullptr;
|
||||
static expr * g_uint32 = nullptr;
|
||||
static expr * g_uint64 = nullptr;
|
||||
|
||||
optional<expr> to_uint_type(unsigned nbytes) {
|
||||
switch (nbytes) {
|
||||
case 1: return some_expr(*g_uint8);
|
||||
case 2: return some_expr(*g_uint16);
|
||||
case 4: return some_expr(*g_uint32);
|
||||
case 8: return some_expr(*g_uint64);
|
||||
default: return none_expr();
|
||||
}
|
||||
}
|
||||
|
||||
unsigned get_num_nested_lambdas(expr e) {
|
||||
unsigned r = 0;
|
||||
while (is_lambda(e)) {
|
||||
|
|
@ -363,9 +378,7 @@ bool is_runtime_scalar_type(name const & n) {
|
|||
n == get_uint16_name() ||
|
||||
n == get_uint32_name() ||
|
||||
n == get_uint64_name() ||
|
||||
n == get_usize_name() ||
|
||||
n == get_bool_name() ||
|
||||
n == get_unit_name();
|
||||
n == get_usize_name();
|
||||
}
|
||||
|
||||
bool is_runtime_builtin_cnstr(name const & n) {
|
||||
|
|
@ -409,6 +422,10 @@ void initialize_compiler_util() {
|
|||
g_neutral_expr = new expr(mk_constant("_neutral_"));
|
||||
g_unreachable_expr = new expr(mk_constant("_unreachable_"));
|
||||
g_object_type = new expr(mk_constant("_obj_"));
|
||||
g_uint8 = new expr(mk_constant(get_uint8_name()));
|
||||
g_uint16 = new expr(mk_constant(get_uint16_name()));
|
||||
g_uint32 = new expr(mk_constant(get_uint32_name()));
|
||||
g_uint64 = new expr(mk_constant(get_uint64_name()));
|
||||
|
||||
register_system_attribute(basic_attribute::with_check(
|
||||
"inline", "mark definition to always be inlined",
|
||||
|
|
@ -447,5 +464,9 @@ void finalize_compiler_util() {
|
|||
delete g_neutral_expr;
|
||||
delete g_unreachable_expr;
|
||||
delete g_object_type;
|
||||
delete g_uint8;
|
||||
delete g_uint16;
|
||||
delete g_uint32;
|
||||
delete g_uint64;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -20,6 +20,8 @@ namespace lean {
|
|||
Remark: if the inductive datatype `I` has more than `2^32` constructors (very unlikely), the result is also `none`. */
|
||||
optional<unsigned> is_enum_type(environment const & env, name const & I);
|
||||
|
||||
optional<expr> to_uint_type(unsigned nbytes);
|
||||
|
||||
/* A "compiler" declaration `x := e` */
|
||||
typedef pair_ref<name, expr> comp_decl;
|
||||
typedef list_ref<comp_decl> comp_decls;
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue