I have two high-level notes on this, based on reading the description and
glancing at the code:
1) I'd be open to supporting c_ptrTo for any DefaultRectangular array
rather than limiting it to arrays of rank 1. (I.e., I'd say that
any array whose storage is contiguous in memory should be passable
to an extern C function expecting an array regardless of rank).
2) I would've taken the approach of implementing this through the domain
map standard interface rather than externally to it. I.e., have the
domain map say (as a param?) whether or not the array's data is
contiguous in memory; and if it is, have it support a routine that
returns the _ddata pointing to the data. Rationales for this:
(1) lower overhead (?); (2) one centralized location doesn't need
to know about all possible domain maps. Of course, this change
could be made at some future time as we make the support for
extern arrays even more straightforward.
-Brad
On Wed, 15 Jan 2014, Michael Ferguson wrote:
> Allow casts between c_ptr types and allow c_ptrTo on arrays.
>
> This patch enables casts (by providing a _cast proc) for
> c_ptr types and also creates a special version of c_ptrTo
> for arrays that checks for a 1-D rectangular arrayand
> returns a pointer to the first element.
>
> I also changed the name of the extern function c_ptrTo
> to _c_ptrTo so that c_ptrTo is the version with the extra
> checks (that normally just calls c_ptrTo which just returns
> the original pointer anyway).
>
> Index: modules/standard/SysBasic.chpl
> ===================================================================
> --- modules/standard/SysBasic.chpl (revision 22538)
> +++ modules/standard/SysBasic.chpl (working copy)
> @@ -60,7 +60,11 @@
> inline proc _cast(type t, x) where t:c_ptr && x:_nilType {
> return __primitive("cast", t, x);
> }
> +inline proc _cast(type t, x) where t:c_ptr && x.type:c_ptr {
> + return __primitive("cast", t, x);
> +}
> +
> inline proc c_calloc(type eltType, size: integral) {
> var ret:c_ptr(eltType);
> __primitive("array_alloc", ret, eltType, size);
> @@ -95,8 +99,20 @@
> inline proc _cond_test(x: c_ptr) return x != nil;
> inline proc !(x: c_ptr) return x == nil;
> -extern proc c_ptrTo(ref x:?t):c_ptr(t);
> +extern proc _c_ptrTo(ref x:?t):c_ptr(t);
> +inline proc c_ptrTo(arr: []) where isRectangularArr(arr) && arr.rank == 1 {
> + return _c_ptrTo(arr[arr.domain.low]);
> +}
> +inline proc c_ptrTo(ref x:?t):c_ptr(t)
> +{
> + if isArrayType(t) then
> + compilerError("c_ptrTo unsupported array type");
> + if isDomainType(t) then
> + compilerError("c_ptrTo domain type not supported");
> + // Other cases should be avoided, e.g. sync vars
> + return _c_ptrTo(x);
> +}
> // C strings
> //extern type c_string; is a built-in primitive type
> Index: runtime/include/chpltypes.h
> ===================================================================
> --- runtime/include/chpltypes.h (revision 22538)
> +++ runtime/include/chpltypes.h (working copy)
> @@ -25,7 +25,7 @@
> typedef void* c_void_ptr;
> #define c_nil NULL
> static inline c_int is_c_nil(void* x) { return x==NULL; }
> -static inline void* c_ptrTo(void* x) { return x; }
> +static inline void* _c_ptrTo(void* x) { return x; }
> typedef const char* c_string;
> typedef enum {
> Index: test/extern/ferguson/tuple_to_pointer.chpl
> ===================================================================
> --- test/extern/ferguson/tuple_to_pointer.chpl (revision 22538)
> +++ test/extern/ferguson/tuple_to_pointer.chpl (working copy)
> @@ -1,13 +1,13 @@
> -extern proc printit(x:c_ptr(c_int), n:c_int);
> +extern proc printarr(x:c_ptr(c_int), n:c_int);
> proc go() {
> var t:10*c_int;
> for i in 1..10 do t[i] = i:c_int;
> writeln(t);
> - printit(c_ptrTo(t[1]), 10);
> - printit(c_ptrTo(t), 10);
> + printarr(c_ptrTo(t[1]), 10);
> + printarr(c_ptrTo(t):c_ptr(c_int), 10);
> }
> go();
> Index: test/extern/ferguson/c_ptrs.h
> ===================================================================
> --- test/extern/ferguson/c_ptrs.h (revision 22538)
> +++ test/extern/ferguson/c_ptrs.h (working copy)
> @@ -8,6 +8,16 @@
> printf("printme(%i)\n", *x);
> }
> +static void printarr(int* x, int n) {
> + int i;
> + printf("printme[0..%i] = ", n-1);
> + for( i = 0; i < n; i++ ) {
> + printf("%i ", x[i]);
> + }
> + printf("\n");
> +}
> +
> +
> static int* getit(void) {
> static int static_value = 22;
> return &static_value;
> Index: test/extern/ferguson/c_ptr_casting.compopts
> ===================================================================
> --- test/extern/ferguson/c_ptr_casting.compopts (revision 22538)
> +++ test/extern/ferguson/c_ptr_casting.compopts (working copy)
> @@ -1 +1 @@
> -print_elements.h
> +c_ptrs.h
> Index: test/extern/ferguson/array_to_pointer.compopts
> ===================================================================
> --- test/extern/ferguson/array_to_pointer.compopts (revision 22538)
> +++ test/extern/ferguson/array_to_pointer.compopts (working copy)
> @@ -1 +1 @@
> -print_elements.h
> +c_ptrs.h
> Index: test/extern/ferguson/tuple_to_pointer.compopts
> ===================================================================
> --- test/extern/ferguson/tuple_to_pointer.compopts (revision 22538)
> +++ test/extern/ferguson/tuple_to_pointer.compopts (working copy)
> @@ -1 +1 @@
> -print_elements.h
> +c_ptrs.h
> Index: test/extern/ferguson/c_ptr_casting.good
> ===================================================================
> --- test/extern/ferguson/c_ptr_casting.good (revision 22538)
> +++ test/extern/ferguson/c_ptr_casting.good (working copy)
> @@ -1,2 +1,2 @@
> (x = 1) (x = 2) (x = 3) (x = 4) (x = 5) (x = 6) (x = 7) (x = 8) (x = 9) (x =
> 10)
> -1 2 3 4 5 6 7 8 9 10
> +printme[0..9] = 1 2 3 4 5 6 7 8 9 10
> Index: test/extern/ferguson/array_to_pointer.good
> ===================================================================
> --- test/extern/ferguson/array_to_pointer.good (revision 22538)
> +++ test/extern/ferguson/array_to_pointer.good (working copy)
> @@ -1,3 +1,3 @@
> 1 2 3 4 5 6 7 8 9 10
> -1 2 3 4 5 6 7 8 9 10
> -1 2 3 4 5 6 7 8 9 10
> +printme[0..9] = 1 2 3 4 5 6 7 8 9 10
> +printme[0..9] = 1 2 3 4 5 6 7 8 9 10
> Index: test/extern/ferguson/tuple_to_pointer.good
> ===================================================================
> --- test/extern/ferguson/tuple_to_pointer.good (revision 22538)
> +++ test/extern/ferguson/tuple_to_pointer.good (working copy)
> @@ -1,3 +1,3 @@
> (1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
> -1 2 3 4 5 6 7 8 9 10
> -1 2 3 4 5 6 7 8 9 10
> +printme[0..9] = 1 2 3 4 5 6 7 8 9 10
> +printme[0..9] = 1 2 3 4 5 6 7 8 9 10
> Index: test/extern/ferguson/c_ptr_casting.chpl
> ===================================================================
> --- test/extern/ferguson/c_ptr_casting.chpl (revision 22538)
> +++ test/extern/ferguson/c_ptr_casting.chpl (working copy)
> @@ -1,4 +1,4 @@
> -extern proc printit(x:c_ptr(c_int), n:c_int);
> +extern proc printarr(x:c_ptr(c_int), n:c_int);
> record R {
> var x: c_int;
> @@ -10,7 +10,7 @@
> for i in 1..10 do a[i] = new R(i:c_int);
> writeln(a);
> - //printit(c_ptrTo(a[1]):c_ptr(c_int));
> + printarr(c_ptrTo(a[1]):c_ptr(c_int), 10);
> }
> go();
> Index: test/extern/ferguson/array_to_pointer.chpl
> ===================================================================
> --- test/extern/ferguson/array_to_pointer.chpl (revision 22538)
> +++ test/extern/ferguson/array_to_pointer.chpl (working copy)
> @@ -1,12 +1,12 @@
> -extern proc printit(x:c_ptr(c_int), n:c_int);
> +extern proc printarr(x:c_ptr(c_int), n:c_int);
> proc go() {
> var a = for i in 1..10 do i:c_int;
> writeln(a);
> - printit(c_ptrTo(a[1]), 10);
> - printit(c_ptrTo(a), 10);
> + printarr(c_ptrTo(a[1]), 10);
> + printarr(c_ptrTo(a), 10);
> }
> go();
>
>
>
------------------------------------------------------------------------------
CenturyLink Cloud: The Leader in Enterprise Cloud Services.
Learn Why More Businesses Are Choosing CenturyLink Cloud For
Critical Workloads, Development Environments & Everything In Between.
Get a Quote or Start a Free Trial Today.
http://pubads.g.doubleclick.net/gampad/clk?id=119420431&iu=/4140/ostg.clktrk
_______________________________________________
Chapel-developers mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/chapel-developers