From 1c9c909456715ea4dd80e0467fd1bc9e5d2268f7 Mon Sep 17 00:00:00 2001 From: Dylon Edwards Date: Wed, 22 Jun 2022 03:21:21 -0400 Subject: [PATCH 1/3] Adds support for str type to ccall --- src/runtime/ltypes/ltypes.py | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/src/runtime/ltypes/ltypes.py b/src/runtime/ltypes/ltypes.py index 3a9e8aa2e1..fcf39455e5 100644 --- a/src/runtime/ltypes/ltypes.py +++ b/src/runtime/ltypes/ltypes.py @@ -129,6 +129,8 @@ def convert_type_to_ctype(arg): return ctypes.c_int8 elif arg == CPtr: return ctypes.c_void_p + elif arg == str: + return ctypes.c_char_p elif arg is None: raise NotImplementedError("Type cannot be None") elif isinstance(arg, Array): @@ -176,7 +178,13 @@ def get_crtlib_path(): def __call__(self, *args, **kwargs): if len(kwargs) > 0: raise Exception("kwargs are not supported") - return self.cf(*args) + new_args = [] + for arg in args: + if isinstance(arg, str): + new_args.append(arg.encode("utf-8")) + else: + new_args.append(arg) + return self.cf(*new_args) def ccall(f): From 16c681a6ea0a2b420a1031fb98ea43a7c09ad77e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ond=C5=99ej=20=C4=8Cert=C3=ADk?= Date: Wed, 22 Jun 2022 12:03:45 +0300 Subject: [PATCH 2/3] Add a test for str in C interoperation --- integration_tests/test_c_interop_02.py | 13 +++++++++++++ integration_tests/test_c_interop_02b.c | 6 ++++++ integration_tests/test_c_interop_02b.h | 1 + 3 files changed, 20 insertions(+) diff --git a/integration_tests/test_c_interop_02.py b/integration_tests/test_c_interop_02.py index 893360a005..c2e5ed4bba 100644 --- a/integration_tests/test_c_interop_02.py +++ b/integration_tests/test_c_interop_02.py @@ -24,6 +24,10 @@ def f_i16_i16(x: i16) -> i16: def f_i8_i8(x: i8) -> i8: pass +@ccall +def f_str_i32(x: str) -> i32: + pass + def test_c_callbacks(): xf64: f64 xf64 = 3.3 @@ -49,4 +53,13 @@ def test_c_callbacks(): xi8 = 3 assert f_i8_i8(xi8) == 4 + assert f_str_i32("Hello World!") == 12 + assert f_str_i32("abc") == 3 + assert f_str_i32("a") == 1 + assert f_str_i32("") == 0 + x: str = "Hello World!" + assert f_str_i32(x) == 12 + x = "abc" + assert f_str_i32(x) == 3 + test_c_callbacks() diff --git a/integration_tests/test_c_interop_02b.c b/integration_tests/test_c_interop_02b.c index ded7af3a2c..2dfde29304 100644 --- a/integration_tests/test_c_interop_02b.c +++ b/integration_tests/test_c_interop_02b.c @@ -1,3 +1,5 @@ +#include + #include "test_c_interop_02b.h" double f_f64_f64(double x) { @@ -23,3 +25,7 @@ int16_t f_i16_i16(int16_t x) { int8_t f_i8_i8(int8_t x) { return x+1; } + +int32_t f_str_i32(char *x) { + return strlen(x); +} diff --git a/integration_tests/test_c_interop_02b.h b/integration_tests/test_c_interop_02b.h index fdf677aa9f..331f8a9103 100644 --- a/integration_tests/test_c_interop_02b.h +++ b/integration_tests/test_c_interop_02b.h @@ -10,6 +10,7 @@ int64_t f_i64_i64(int64_t x); int32_t f_i32_i32(int32_t x); int16_t f_i16_i16(int16_t x); int8_t f_i8_i8 (int8_t x); +int32_t f_str_i32(char *x); #endif // TEST_C_INTEROP_02B From a7f9085facb5bd64b2f0c3161c264ec320b1eba4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ond=C5=99ej=20=C4=8Cert=C3=ADk?= Date: Wed, 22 Jun 2022 12:23:10 +0300 Subject: [PATCH 3/3] C backend: Implement string type for declarations --- src/libasr/codegen/asr_to_c.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/libasr/codegen/asr_to_c.cpp b/src/libasr/codegen/asr_to_c.cpp index bcca0b4cfc..bc43144892 100644 --- a/src/libasr/codegen/asr_to_c.cpp +++ b/src/libasr/codegen/asr_to_c.cpp @@ -114,7 +114,9 @@ class ASRToCVisitor : public BaseCCPPVisitor std::string dims = convert_dims_c(t->n_dims, t->m_dims); sub = format_type_c(dims, "bool", v.m_name, use_ref, dummy); } else if (ASRUtils::is_character(*v.m_type)) { - // TODO + ASR::Character_t *t = ASR::down_cast(v.m_type); + std::string dims = convert_dims_c(t->n_dims, t->m_dims); + sub = format_type_c(dims, "char *", v.m_name, use_ref, dummy); } else if (ASR::is_a(*v.m_type)) { std::string indent(indentation_level*indentation_spaces, ' '); ASR::Derived_t *t = ASR::down_cast(v.m_type);