Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
Merge branch 'main' into dict_keys_values
  • Loading branch information
kabra1110 committed Jul 20, 2023
commit 30b2cf6e9d96b7d8a44f152cf9312207d41b7f90
3 changes: 3 additions & 0 deletions integration_tests/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -487,6 +487,9 @@ RUN(NAME test_dict_13 LABELS cpython llvm c)
RUN(NAME test_dict_bool LABELS cpython llvm)
RUN(NAME test_dict_increment LABELS cpython llvm)
RUN(NAME test_dict_keys_values LABELS cpython llvm)
RUN(NAME test_set_len LABELS cpython llvm)
RUN(NAME test_set_add LABELS cpython llvm)
RUN(NAME test_set_remove LABELS cpython llvm)
RUN(NAME test_for_loop LABELS cpython llvm c)
RUN(NAME modules_01 LABELS cpython llvm c wasm wasm_x86 wasm_x64)
RUN(NAME modules_02 LABELS cpython llvm c wasm wasm_x86 wasm_x64)
Expand Down
43 changes: 39 additions & 4 deletions src/libasr/codegen/asr_to_llvm.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1695,7 +1695,7 @@ class ASRToLLVMVisitor : public ASR::BaseVisitor<ASRToLLVMVisitor>
this->visit_expr(*m_arg);
llvm::Value* pdict = tmp;

set_dict_api(dict_type);
llvm_utils->set_dict_api(dict_type);
if(llvm_utils->dict_api == dict_api_sc.get()) {
throw CodeGenError("dict.keys and dict.values are only implemented "
"for linear probing for now", loc);
Expand All @@ -1706,11 +1706,10 @@ class ASRToLLVMVisitor : public ASR::BaseVisitor<ASRToLLVMVisitor>
bool is_list_local = false;
ASR::dimension_t* m_dims_local = nullptr;
int n_dims_local = -1, a_kind_local = -1;
llvm::Type* llvm_el_type = get_type_from_ttype_t(el_type,
nullptr,
llvm::Type* llvm_el_type = llvm_utils->get_type_from_ttype_t(el_type, nullptr,
ASR::storage_typeType::Default, is_array_type_local,
is_malloc_array_type_local, is_list_local, m_dims_local,
n_dims_local, a_kind_local);
n_dims_local, a_kind_local, module.get());
std::string type_code = ASRUtils::get_type_code(el_type);
int32_t type_size = -1;
if( ASR::is_a<ASR::Character_t>(*el_type) ||
Expand All @@ -1731,6 +1730,34 @@ class ASRToLLVMVisitor : public ASR::BaseVisitor<ASRToLLVMVisitor>
tmp = el_list;
}

void generate_SetAdd(ASR::expr_t* m_arg, ASR::expr_t* m_ele) {
ASR::ttype_t* asr_el_type = ASRUtils::get_contained_type(ASRUtils::expr_type(m_arg));
int64_t ptr_loads_copy = ptr_loads;
ptr_loads = 0;
this->visit_expr(*m_arg);
llvm::Value* pset = tmp;

ptr_loads = 2;
this->visit_expr_wrapper(m_ele, true);
ptr_loads = ptr_loads_copy;
llvm::Value *el = tmp;
set_api->write_item(pset, el, module.get(), asr_el_type, name2memidx);
}

void generate_SetRemove(ASR::expr_t* m_arg, ASR::expr_t* m_ele) {
ASR::ttype_t* asr_el_type = ASRUtils::get_contained_type(ASRUtils::expr_type(m_arg));
int64_t ptr_loads_copy = ptr_loads;
ptr_loads = 0;
this->visit_expr(*m_arg);
llvm::Value* pset = tmp;

ptr_loads = 2;
this->visit_expr_wrapper(m_ele, true);
ptr_loads = ptr_loads_copy;
llvm::Value *el = tmp;
set_api->remove_item(pset, el, *module, asr_el_type);
}

void visit_IntrinsicFunction(const ASR::IntrinsicFunction_t& x) {
switch (static_cast<ASRUtils::IntrinsicFunctions>(x.m_intrinsic_id)) {
case ASRUtils::IntrinsicFunctions::ListIndex: {
Expand Down Expand Up @@ -1782,6 +1809,14 @@ class ASRToLLVMVisitor : public ASR::BaseVisitor<ASRToLLVMVisitor>
generate_DictElems(x.m_args[0], 1, x.base.base.loc);
break;
}
case ASRUtils::IntrinsicFunctions::SetAdd: {
generate_SetAdd(x.m_args[0], x.m_args[1]);
break;
}
case ASRUtils::IntrinsicFunctions::SetRemove: {
generate_SetRemove(x.m_args[0], x.m_args[1]);
break;
}
case ASRUtils::IntrinsicFunctions::Exp: {
switch (x.m_overload_id) {
case 0: {
Expand Down
188 changes: 157 additions & 31 deletions src/libasr/pass/intrinsic_function_registry.h
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,15 @@ enum class IntrinsicFunctions : int64_t {
ListPop,
DictKeys,
DictValues,
SetAdd,
SetRemove,
Sum,
Product,
Max,
MaxVal,
Min,
MinVal,
Merge,
SymbolicSymbol,
SymbolicAdd,
SymbolicSub,
Expand Down Expand Up @@ -93,6 +102,8 @@ inline std::string get_intrinsic_name(int x) {
INTRINSIC_NAME_CASE(Partition)
INTRINSIC_NAME_CASE(ListReverse)
INTRINSIC_NAME_CASE(ListPop)
INTRINSIC_NAME_CASE(DictKeys)
INTRINSIC_NAME_CASE(DictValues)
INTRINSIC_NAME_CASE(SetAdd)
INTRINSIC_NAME_CASE(SetRemove)
INTRINSIC_NAME_CASE(Sum)
Expand Down Expand Up @@ -1343,6 +1354,104 @@ static inline ASR::asr_t* create_DictValues(Allocator& al, const Location& loc,

} // namespace DictValues

namespace SetAdd {

static inline void verify_args(const ASR::IntrinsicFunction_t& x, diag::Diagnostics& diagnostics) {
ASRUtils::require_impl(x.n_args == 2, "Call to set.add must have exactly one argument",
x.base.base.loc, diagnostics);
ASRUtils::require_impl(ASR::is_a<ASR::Set_t>(*ASRUtils::expr_type(x.m_args[0])),
"First argument to set.add must be of set type",
x.base.base.loc, diagnostics);
ASRUtils::require_impl(ASRUtils::check_equal_type(ASRUtils::expr_type(x.m_args[1]),
ASRUtils::get_contained_type(ASRUtils::expr_type(x.m_args[0]))),
"Second argument to set.add must be of same type as set's element type",
x.base.base.loc, diagnostics);
ASRUtils::require_impl(x.m_type == nullptr,
"Return type of set.add must be empty",
x.base.base.loc, diagnostics);
}

static inline ASR::expr_t *eval_set_add(Allocator &/*al*/,
const Location &/*loc*/, Vec<ASR::expr_t*>& /*args*/) {
// TODO: To be implemented for SetConstant expression
return nullptr;
}

static inline ASR::asr_t* create_SetAdd(Allocator& al, const Location& loc,
Vec<ASR::expr_t*>& args,
const std::function<void (const std::string &, const Location &)> err) {
if (args.size() != 2) {
err("Call to set.add must have exactly one argument", loc);
}
if (!ASRUtils::check_equal_type(ASRUtils::expr_type(args[1]),
ASRUtils::get_contained_type(ASRUtils::expr_type(args[0])))) {
err("Argument to set.add must be of same type as set's "
"element type", loc);
}

Vec<ASR::expr_t*> arg_values;
arg_values.reserve(al, args.size());
for( size_t i = 0; i < args.size(); i++ ) {
arg_values.push_back(al, ASRUtils::expr_value(args[i]));
}
ASR::expr_t* compile_time_value = eval_set_add(al, loc, arg_values);
return ASR::make_Expr_t(al, loc,
ASRUtils::EXPR(ASR::make_IntrinsicFunction_t(al, loc,
static_cast<int64_t>(ASRUtils::IntrinsicFunctions::SetAdd),
args.p, args.size(), 0, nullptr, compile_time_value)));
}

} // namespace SetAdd

namespace SetRemove {

static inline void verify_args(const ASR::IntrinsicFunction_t& x, diag::Diagnostics& diagnostics) {
ASRUtils::require_impl(x.n_args == 2, "Call to set.remove must have exactly one argument",
x.base.base.loc, diagnostics);
ASRUtils::require_impl(ASR::is_a<ASR::Set_t>(*ASRUtils::expr_type(x.m_args[0])),
"First argument to set.remove must be of set type",
x.base.base.loc, diagnostics);
ASRUtils::require_impl(ASRUtils::check_equal_type(ASRUtils::expr_type(x.m_args[1]),
ASRUtils::get_contained_type(ASRUtils::expr_type(x.m_args[0]))),
"Second argument to set.remove must be of same type as set's element type",
x.base.base.loc, diagnostics);
ASRUtils::require_impl(x.m_type == nullptr,
"Return type of set.remove must be empty",
x.base.base.loc, diagnostics);
}

static inline ASR::expr_t *eval_set_remove(Allocator &/*al*/,
const Location &/*loc*/, Vec<ASR::expr_t*>& /*args*/) {
// TODO: To be implemented for SetConstant expression
return nullptr;
}

static inline ASR::asr_t* create_SetRemove(Allocator& al, const Location& loc,
Vec<ASR::expr_t*>& args,
const std::function<void (const std::string &, const Location &)> err) {
if (args.size() != 2) {
err("Call to set.remove must have exactly one argument", loc);
}
if (!ASRUtils::check_equal_type(ASRUtils::expr_type(args[1]),
ASRUtils::get_contained_type(ASRUtils::expr_type(args[0])))) {
err("Argument to set.remove must be of same type as set's "
"element type", loc);
}

Vec<ASR::expr_t*> arg_values;
arg_values.reserve(al, args.size());
for( size_t i = 0; i < args.size(); i++ ) {
arg_values.push_back(al, ASRUtils::expr_value(args[i]));
}
ASR::expr_t* compile_time_value = eval_set_remove(al, loc, arg_values);
return ASR::make_Expr_t(al, loc,
ASRUtils::EXPR(ASR::make_IntrinsicFunction_t(al, loc,
static_cast<int64_t>(ASRUtils::IntrinsicFunctions::SetRemove),
args.p, args.size(), 0, nullptr, compile_time_value)));
}

} // namespace SetRemove

namespace Any {

static inline void verify_array(ASR::expr_t* array, ASR::ttype_t* return_type,
Expand Down Expand Up @@ -3013,6 +3122,22 @@ namespace IntrinsicFunctionRegistry {
{nullptr, &DictKeys::verify_args}},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::DictValues),
{nullptr, &DictValues::verify_args}},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::ListPop),
{nullptr, &ListPop::verify_args}},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::SetAdd),
{nullptr, &SetAdd::verify_args}},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::SetRemove),
{nullptr, &SetRemove::verify_args}},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::Max),
{&Max::instantiate_Max, &Max::verify_args}},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::MaxVal),
{&MaxVal::instantiate_MaxVal, &MaxVal::verify_args}},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::Min),
{&Min::instantiate_Min, &Min::verify_args}},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::MinVal),
{&MinVal::instantiate_MinVal, &MinVal::verify_args}},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::Merge),
{&Merge::instantiate_Merge, &Merge::verify_args}},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::SymbolicSymbol),
{nullptr, &SymbolicSymbol::verify_args}},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::SymbolicAdd),
Expand Down Expand Up @@ -3085,6 +3210,26 @@ namespace IntrinsicFunctionRegistry {
"dict.keys"},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::DictValues),
"dict.values"},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::SetAdd),
"set.add"},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::SetRemove),
"set.remove"},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::Any),
"any"},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::Sum),
"sum"},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::Product),
"product"},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::Max),
"max"},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::MaxVal),
"maxval"},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::Min),
"min"},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::MinVal),
"minval"},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::Merge),
"merge"},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::SymbolicSymbol),
"Symbol"},
{static_cast<int64_t>(ASRUtils::IntrinsicFunctions::SymbolicAdd),
Expand Down Expand Up @@ -3147,6 +3292,14 @@ namespace IntrinsicFunctionRegistry {
{"list.pop", {&ListPop::create_ListPop, &ListPop::eval_list_pop}},
{"dict.keys", {&DictKeys::create_DictKeys, &DictKeys::eval_dict_keys}},
{"dict.values", {&DictValues::create_DictValues, &DictValues::eval_dict_values}},
{"set.add", {&SetAdd::create_SetAdd, &SetAdd::eval_set_add}},
{"set.remove", {&SetRemove::create_SetRemove, &SetRemove::eval_set_remove}},
{"max0", {&Max::create_Max, &Max::eval_Max}},
{"maxval", {&MaxVal::create_MaxVal, &MaxVal::eval_MaxVal}},
{"min0", {&Min::create_Min, &Min::eval_Min}},
{"min", {&Min::create_Min, &Min::eval_Min}},
{"minval", {&MinVal::create_MinVal, &MinVal::eval_MinVal}},
{"merge", {&Merge::create_Merge, &Merge::eval_Merge}},
{"Symbol", {&SymbolicSymbol::create_SymbolicSymbol, &SymbolicSymbol::eval_SymbolicSymbol}},
{"SymbolicAdd", {&SymbolicAdd::create_SymbolicAdd, &SymbolicAdd::eval_SymbolicAdd}},
{"SymbolicSub", {&SymbolicSub::create_SymbolicSub, &SymbolicSub::eval_SymbolicSub}},
Expand Down Expand Up @@ -3302,37 +3455,10 @@ namespace IntrinsicImpureFunctionRegistry {

inline std::string get_impure_intrinsic_name(int x) {
switch (x) {
INTRINSIC_NAME_CASE(Sin)
INTRINSIC_NAME_CASE(Cos)
INTRINSIC_NAME_CASE(Tan)
INTRINSIC_NAME_CASE(Asin)
INTRINSIC_NAME_CASE(Acos)
INTRINSIC_NAME_CASE(Atan)
INTRINSIC_NAME_CASE(Sinh)
INTRINSIC_NAME_CASE(Cosh)
INTRINSIC_NAME_CASE(Tanh)
INTRINSIC_NAME_CASE(Gamma)
INTRINSIC_NAME_CASE(LogGamma)
INTRINSIC_NAME_CASE(Abs)
INTRINSIC_NAME_CASE(Exp)
INTRINSIC_NAME_CASE(Exp2)
INTRINSIC_NAME_CASE(Expm1)
INTRINSIC_NAME_CASE(Any)
INTRINSIC_NAME_CASE(ListIndex)
INTRINSIC_NAME_CASE(Partition)
INTRINSIC_NAME_CASE(ListReverse)
INTRINSIC_NAME_CASE(ListPop)
INTRINSIC_NAME_CASE(DictKeys)
INTRINSIC_NAME_CASE(DictValues)
INTRINSIC_NAME_CASE(SymbolicSymbol)
INTRINSIC_NAME_CASE(SymbolicAdd)
INTRINSIC_NAME_CASE(SymbolicSub)
INTRINSIC_NAME_CASE(SymbolicMul)
INTRINSIC_NAME_CASE(SymbolicDiv)
INTRINSIC_NAME_CASE(SymbolicPow)
INTRINSIC_NAME_CASE(SymbolicPi)
INTRINSIC_NAME_CASE(SymbolicInteger)
INTRINSIC_NAME_CASE(Sum)
IMPURE_INTRINSIC_NAME_CASE(IsIostatEnd)
IMPURE_INTRINSIC_NAME_CASE(IsIostatEor)
INTRINSIC_NAME_CASE(Max)
INTRINSIC_NAME_CASE(Min)
default : {
throw LCompilersException("pickle: intrinsic_id not implemented");
}
Expand Down
28 changes: 28 additions & 0 deletions src/lpython/semantics/python_attribute_eval.h
Original file line number Diff line number Diff line change
Expand Up @@ -414,6 +414,34 @@ struct AttributeHandler {
{ throw SemanticError(msg, loc); });
}

static ASR::asr_t* eval_symbolic_diff(ASR::expr_t *s, Allocator &al, const Location &loc,
Vec<ASR::expr_t*> &args, diag::Diagnostics &/*diag*/) {
Vec<ASR::expr_t*> args_with_list;
args_with_list.reserve(al, args.size() + 1);
args_with_list.push_back(al, s);
for(size_t i = 0; i < args.size(); i++) {
args_with_list.push_back(al, args[i]);
}
ASRUtils::create_intrinsic_function create_function =
ASRUtils::IntrinsicFunctionRegistry::get_create_function("diff");
return create_function(al, loc, args_with_list, [&](const std::string &msg, const Location &loc)
{ throw SemanticError(msg, loc); });
}

static ASR::asr_t* eval_symbolic_expand(ASR::expr_t *s, Allocator &al, const Location &loc,
Vec<ASR::expr_t*> &args, diag::Diagnostics &/*diag*/) {
Vec<ASR::expr_t*> args_with_list;
args_with_list.reserve(al, args.size() + 1);
args_with_list.push_back(al, s);
for(size_t i = 0; i < args.size(); i++) {
args_with_list.push_back(al, args[i]);
}
ASRUtils::create_intrinsic_function create_function =
ASRUtils::IntrinsicFunctionRegistry::get_create_function("expand");
return create_function(al, loc, args_with_list, [&](const std::string &msg, const Location &loc)
{ throw SemanticError(msg, loc); });
}

}; // AttributeHandler

} // namespace LCompilers::LPython
Expand Down
You are viewing a condensed version of this merge commit. You can view the full changes here.