1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
|
-
+
+
+
+
+
+
+
+
-
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
-
+
+
+
+
+
+
+
|
#include "g0api/g0api.h"
#include "eir/eir.h"
#include "builtins/helpers.h"
using namespace goose;
using namespace goose::g0api;
namespace
{
template< typename T >
void SetupWrapperForType( Env& e, StringId name )
void SetupWrapperForType( Env& e, StringId name, const ptr< OverloadSet >& pEquals, const ptr< OverloadSet >& pNotEquals )
{
DefineConstant( e, name, GetValueType< TypeWrapper< T > >() );
using reftype = CustomPattern< Value, ReferenceType::PatternMutableOfType< TypeWrapper< T > > >;
auto type = ValueToEIR( ToValue( builtins::ReferenceType( GetValueType< TypeWrapper< T > >(), TSID( mut ) ) ) );
RegisterBuiltinFunc< Intrinsic< Value ( reftype ) > >( e, e.extInitialize(),
[]( auto&& c, const Value& r )
{
// Do nothing: the types we're wrapping are default initialized anyway.
// The only purpose of this Initialize overload is to let goose know that
// the type has a default initialization.
return Value( GetValueType< void >(), 0U );
} );
using constreftype = CustomPattern<
TypeWrapper< T >, ReferenceType::PatternConstOfType< TypeWrapper< T > > >;
RegisterBuiltinFunc< bool ( constreftype, constreftype ) >( e, pEquals,
[]( const TypeWrapper< T >& lhs, const TypeWrapper< T >& rhs )
{
return lhs.get() == rhs.get();
} );
// TODO: assignment operator, equality operator, inequality operator
RegisterBuiltinFunc< bool ( constreftype, constreftype ) >( e, pNotEquals,
[]( const TypeWrapper< T >& lhs, const TypeWrapper< T >& rhs )
{
return lhs.get() != rhs.get();
} );
}
}
namespace goose::g0api
{
void SetupTypeWrappers( Env& e )
{
auto pEquals = GetOverloadSet( e, "operator_equals"_sid );
auto pNotEquals = GetOverloadSet( e, "operator_not_equals"_sid );
// Equality operator for term wrapper
RegisterBuiltinFunc< bool ( TermWrapper, TermWrapper ) >( e, pEquals,
[]( const TermWrapper& lhs, const TermWrapper& rhs )
{
return lhs.get() == rhs.get();
} );
RegisterBuiltinFunc< bool ( TermWrapper, TermWrapper ) >( e, pNotEquals,
[]( const TermWrapper& lhs, const TermWrapper& rhs )
{
return lhs.get() != rhs.get();
} );
SetupWrapperForType< LocationId >( e, "LocationId"_sid );
SetupWrapperForType< LocationId >( e, "LocationId"_sid, pEquals, pNotEquals );
SetupWrapperForType< StringId >( e, "StringId"_sid, pEquals, pNotEquals );
SetupWrapperForType< Hole >( e, "Hole"_sid, pEquals, pNotEquals );
SetupWrapperForType< AnyTerm >( e, "AnyTerm"_sid, pEquals, pNotEquals );
SetupWrapperForType< VecOfLength >( e, "VecOfLength"_sid, pEquals, pNotEquals );
SetupWrapperForType< pvec >( e, "Vec"_sid, pEquals, pNotEquals );
SetupWrapperForType< APSInt >( e, "FixedInt"_sid, pEquals, pNotEquals );
}
}
|