source: libcfa/src/containers/array.hfa @ b9dae14c

arm-ehjacob/cs343-translation
Last change on this file since b9dae14c was b9dae14c, checked in by Michael Brooks <mlbrooks@…>, 3 months ago

Activated syntax, forall( [N] ).

This implementation desugars in the parser, as forall( ztype(N) ) did in
the preprocessor. Semantic analysis is still required to lock down treating N as a
a traditional type (forbid: N x = 17; vector(N) v;). Deferring that work until
the N--value adapters ( Z(17), z(N) ) are settled.

  • Property mode set to 100644
File size: 3.9 KB
Line 
1
2
3// a type whose size is n
4#define Z(n) char[n]
5
6// the inverse of Z(-)
7#define z(N) sizeof(N)
8
9forall( T & ) struct tag {};
10#define ttag(T) ((tag(T)){})
11#define ztag(n) ttag(Z(n))
12
13
14//
15// Single-dim array sruct (with explicit packing and atom)
16//
17
18forall( [N], [S], Timmed &, Tbase & ) {
19    struct arpk {
20        S strides[z(N)];
21    };
22
23    Timmed & ?[?]( arpk(N, S, Timmed, Tbase) & a, ptrdiff_t i ) {
24        return (Timmed &) a.strides[i];
25    }
26
27    Timmed & ?[?]( arpk(N, S, Timmed, Tbase) & a, int i ) {
28        return (Timmed &) a.strides[i];
29    }
30
31    Timmed & ?[?]( arpk(N, S, Timmed, Tbase) & a, size_t i ) {
32        return (Timmed &) a.strides[i];
33    }
34
35    size_t ?`len( arpk(N, S, Timmed, Tbase) & a ) {
36        return z(N);
37    }
38
39    // workaround #226 (and array relevance thereof demonstrated in mike102/otype-slow-ndims.cfa)
40    void ?{}( arpk(N, S, Timmed, Tbase) & this ) {
41        void ?{}( S (&inner)[z(N)] ) {}
42        ?{}(this.strides);
43    }
44    void ^?{}( arpk(N, S, Timmed, Tbase) & this ) {
45        void ^?{}( S (&inner)[z(N)] ) {}
46        ^?{}(this.strides);
47    }
48}
49
50//
51// Sugar for declaring array structure instances
52//
53
54forall( Te )
55Te mkar_( tag(Te) ) {}
56
57forall( [N], ZTags ... , Trslt &, Tatom & | { Trslt mkar_( tag(Tatom), ZTags ); } )
58arpk(N, Trslt, Trslt, Tatom) mkar_( tag(Tatom), tag(N), ZTags ) {}
59
60// based on https://stackoverflow.com/questions/1872220/is-it-possible-to-iterate-over-arguments-in-variadic-macros
61
62    // Make a FOREACH macro
63    #define FE_0(WHAT)
64    #define FE_1(WHAT, X) WHAT(X)
65    #define FE_2(WHAT, X, ...) WHAT(X)FE_1(WHAT, __VA_ARGS__)
66    #define FE_3(WHAT, X, ...) WHAT(X)FE_2(WHAT, __VA_ARGS__)
67    #define FE_4(WHAT, X, ...) WHAT(X)FE_3(WHAT, __VA_ARGS__)
68    #define FE_5(WHAT, X, ...) WHAT(X)FE_4(WHAT, __VA_ARGS__)
69    //... repeat as needed
70
71    #define GET_MACRO(_0,_1,_2,_3,_4,_5,NAME,...) NAME
72    #define FOR_EACH(action,...) \
73    GET_MACRO(_0,__VA_ARGS__,FE_5,FE_4,FE_3,FE_2,FE_1,FE_0)(action,__VA_ARGS__)
74
75#define COMMA_ttag(X) , ttag(X)
76#define array( TE, ...) typeof( mkar_( ttag(TE)  FOR_EACH( COMMA_ttag, __VA_ARGS__ ) ) )
77
78#define COMMA_ztag(X) , ztag(X)
79#define zarray( TE, ...) typeof( mkar_( ttag(TE)  FOR_EACH( COMMA_ztag, __VA_ARGS__ ) ) )
80
81//
82// Sugar for multidimensional indexing
83//
84
85// Core -[[-,-,-]] operator
86
87#ifdef TRY_BROKEN_DESIRED_MD_SUBSCRIPT
88
89// Desired form.  One definition with recursion on IxBC (worked until Jan 2021, see trac #__TODO__)
90
91forall( TA &, TB &, TC &, IxAB, IxBC ... | { TB & ?[?]( TA &, IxAB ); TC & ?[?]( TB &, IxBC ); } )
92TC & ?[?]( TA & this, IxAB ab, IxBC bc ) {
93    return this[ab][bc];
94}
95
96#else
97
98// Workaround form.  Listing all possibilities up to 4 dims.
99
100forall( TA &, TB &, TC &, IxAB_0, IxBC | { TB & ?[?]( TA &, IxAB_0 ); TC & ?[?]( TB &, IxBC ); } )
101TC & ?[?]( TA & this, IxAB_0 ab, IxBC bc ) {
102    return this[ab][bc];
103}
104
105forall( TA &, TB &, TC &, IxAB_0, IxAB_1, IxBC | { TB & ?[?]( TA &, IxAB_0, IxAB_1 ); TC & ?[?]( TB &, IxBC ); } )
106TC & ?[?]( TA & this, IxAB_0 ab0, IxAB_1 ab1, IxBC bc ) {
107    return this[[ab0,ab1]][bc];
108}
109
110forall( TA &, TB &, TC &, IxAB_0, IxAB_1, IxAB_2, IxBC | { TB & ?[?]( TA &, IxAB_0, IxAB_1, IxAB_2 ); TC & ?[?]( TB &, IxBC ); } )
111TC & ?[?]( TA & this, IxAB_0 ab0, IxAB_1 ab1, IxAB_2 ab2, IxBC bc ) {
112    return this[[ab0,ab1,ab2]][bc];
113}
114
115#endif
116
117//
118// Rotation
119//
120
121// Base
122forall( [Nq], [Sq], Tbase & )
123tag(arpk(Nq, Sq, Tbase, Tbase)) enq_( tag(Tbase), tag(Nq), tag(Sq), tag(Tbase) ) {}
124
125// Rec
126forall( [Nq], [Sq], [N], [S], recq &, recr &, Tbase & | { tag(recr) enq_( tag(Tbase), tag(Nq), tag(Sq), tag(recq) ); } )
127tag(arpk(N, S, recr, Tbase)) enq_( tag(Tbase), tag(Nq), tag(Sq), tag(arpk(N, S, recq, Tbase)) ) {}
128
129// Wrapper
130struct all_t {} all;
131forall( [N], [S], Te &, result &, Tbase & | { tag(result) enq_( tag(Tbase), tag(N), tag(S), tag(Te) ); } )
132result & ?[?]( arpk(N, S, Te, Tbase) & this, all_t ) {
133    return (result&) this;
134}
135
136//
137// Trait of array or slice
138//
139
140trait ar(A &, Tv &) {
141    Tv& ?[?]( A&, ptrdiff_t );
142    size_t ?`len( A& );
143};
Note: See TracBrowser for help on using the repository browser.