source: src/ResolvExpr/CommonType.cpp @ 31f4837

Last change on this file since 31f4837 was 31f4837, checked in by JiadaL <j82liang@…>, 2 months ago

Merge branch 'master' of plg.uwaterloo.ca:software/cfa/cfa-cc

  • Property mode set to 100644
File size: 49.8 KB
Line 
1//
2// Cforall Version 1.0.0 Copyright (C) 2015 University of Waterloo
3//
4// The contents of this file are covered under the licence agreement in the
5// file "LICENCE" distributed with Cforall.
6//
7// CommonType.cpp --
8//
9// Author           : Richard C. Bilson
10// Created On       : Sun May 17 06:59:27 2015
11// Last Modified By : Peter A. Buhr
12// Last Modified On : Thu Feb 14 17:10:10 2019
13// Update Count     : 24
14//
15
16#include "CommonType.hpp"
17
18#include <cassert>                       // for strict_dynamic_cast
19#include <map>                           // for _Rb_tree_const_iterator
20#include <utility>                       // for pair
21
22#include "AST/Decl.hpp"
23#include "AST/Pass.hpp"
24#include "AST/Type.hpp"
25#include "Unify.hpp"                     // for unifyExact, WidenMode
26#include "Typeops.hpp"                   // for isFtype
27#include "Tuples/Tuples.hpp"
28
29// #define DEBUG
30#ifdef DEBUG
31#define PRINT(x) x
32#else
33#define PRINT(x)
34#endif
35
36namespace ResolvExpr {
37
38namespace {
39
40        // GENERATED START, DO NOT EDIT
41        // GENERATED BY BasicTypes-gen.cpp
42        #define BT ast::BasicKind::
43        static const ast::BasicKind commonTypes[BT NUMBER_OF_BASIC_TYPES][BT NUMBER_OF_BASIC_TYPES] = { // nearest common ancestor
44                /*                                      B                       C                      SC                      UC                      SI                     SUI
45                                                        I                      UI                      LI                     LUI                     LLI                    LLUI
46                                                       IB                     UIB                     _FH                     _FH                      _F                     _FC
47                                                        F                      FC                     _FX                    _FXC                      FD                    _FDC
48                                                        D                      DC                    F80X                   _FDXC                     F80                     _FB
49                                                    _FLDC                      FB                      LD                     LDC                    _FBX                  _FLDXC
50                                 */
51                                  {
52                /*      B */                BT Bool,                BT Char,          BT SignedChar,        BT UnsignedChar,      BT ShortSignedInt,    BT ShortUnsignedInt,
53                                             BT SignedInt,         BT UnsignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
54                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
55                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
56                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
57                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
58                                  },
59                                  {
60                /*      C */                BT Char,                BT Char,          BT SignedChar,        BT UnsignedChar,      BT ShortSignedInt,    BT ShortUnsignedInt,
61                                             BT SignedInt,         BT UnsignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
62                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
63                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
64                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
65                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
66                                  },
67                                  {
68                /*     SC */          BT SignedChar,          BT SignedChar,          BT SignedChar,        BT UnsignedChar,      BT ShortSignedInt,    BT ShortUnsignedInt,
69                                             BT SignedInt,         BT UnsignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
70                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
71                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
72                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
73                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
74                                  },
75                                  {
76                /*     UC */        BT UnsignedChar,        BT UnsignedChar,        BT UnsignedChar,        BT UnsignedChar,      BT ShortSignedInt,    BT ShortUnsignedInt,
77                                             BT SignedInt,         BT UnsignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
78                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
79                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
80                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
81                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
82                                  },
83                                  {
84                /*     SI */      BT ShortSignedInt,      BT ShortSignedInt,      BT ShortSignedInt,      BT ShortSignedInt,      BT ShortSignedInt,    BT ShortUnsignedInt,
85                                             BT SignedInt,         BT UnsignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
86                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
87                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
88                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
89                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
90                                  },
91                                  {
92                /*    SUI */    BT ShortUnsignedInt,    BT ShortUnsignedInt,    BT ShortUnsignedInt,    BT ShortUnsignedInt,    BT ShortUnsignedInt,    BT ShortUnsignedInt,
93                                             BT SignedInt,         BT UnsignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
94                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
95                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
96                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
97                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
98                                  },
99                                  {
100                /*      I */           BT SignedInt,           BT SignedInt,           BT SignedInt,           BT SignedInt,           BT SignedInt,           BT SignedInt,
101                                             BT SignedInt,         BT UnsignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
102                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
103                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
104                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
105                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
106                                  },
107                                  {
108                /*     UI */         BT UnsignedInt,         BT UnsignedInt,         BT UnsignedInt,         BT UnsignedInt,         BT UnsignedInt,         BT UnsignedInt,
109                                           BT UnsignedInt,         BT UnsignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
110                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
111                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
112                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
113                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
114                                  },
115                                  {
116                /*     LI */       BT LongSignedInt,       BT LongSignedInt,       BT LongSignedInt,       BT LongSignedInt,       BT LongSignedInt,       BT LongSignedInt,
117                                         BT LongSignedInt,       BT LongSignedInt,       BT LongSignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
118                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
119                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
120                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
121                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
122                                  },
123                                  {
124                /*    LUI */     BT LongUnsignedInt,     BT LongUnsignedInt,     BT LongUnsignedInt,     BT LongUnsignedInt,     BT LongUnsignedInt,     BT LongUnsignedInt,
125                                       BT LongUnsignedInt,     BT LongUnsignedInt,     BT LongUnsignedInt,     BT LongUnsignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
126                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
127                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
128                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
129                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
130                                  },
131                                  {
132                /*    LLI */   BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt,
133                                     BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt,   BT LongLongSignedInt, BT LongLongUnsignedInt,
134                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
135                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
136                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
137                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
138                                  },
139                                  {
140                /*   LLUI */ BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt,
141                                   BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt, BT LongLongUnsignedInt,
142                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
143                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
144                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
145                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
146                                  },
147                                  {
148                /*     IB */        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,
149                                          BT SignedInt128,        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,        BT SignedInt128,
150                                          BT SignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
151                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
152                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
153                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
154                                  },
155                                  {
156                /*    UIB */      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,
157                                        BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,      BT UnsignedInt128,
158                                        BT UnsignedInt128,      BT UnsignedInt128,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
159                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
160                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
161                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
162                                  },
163                                  {
164                /*    _FH */            BT uFloat16,            BT uFloat16,            BT uFloat16,            BT uFloat16,            BT uFloat16,            BT uFloat16,
165                                              BT uFloat16,            BT uFloat16,            BT uFloat16,            BT uFloat16,            BT uFloat16,            BT uFloat16,
166                                              BT uFloat16,            BT uFloat16,            BT uFloat16,     BT uFloat16Complex,            BT uFloat32,     BT uFloat32Complex,
167                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
168                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
169                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
170                                  },
171                                  {
172                /*    _FH */     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,
173                                       BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,
174                                       BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat16Complex,     BT uFloat32Complex,     BT uFloat32Complex,
175                                          BT FloatComplex,        BT FloatComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,     BT uFloat64Complex,     BT uFloat64Complex,
176                                         BT DoubleComplex,       BT DoubleComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat128Complex,
177                                      BT uFloat128Complex,    BT uFloat128Complex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
178                                  },
179                                  {
180                /*     _F */            BT uFloat32,            BT uFloat32,            BT uFloat32,            BT uFloat32,            BT uFloat32,            BT uFloat32,
181                                              BT uFloat32,            BT uFloat32,            BT uFloat32,            BT uFloat32,            BT uFloat32,            BT uFloat32,
182                                              BT uFloat32,            BT uFloat32,            BT uFloat32,     BT uFloat32Complex,            BT uFloat32,     BT uFloat32Complex,
183                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
184                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
185                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
186                                  },
187                                  {
188                /*    _FC */     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,
189                                       BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,
190                                       BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,     BT uFloat32Complex,
191                                          BT FloatComplex,        BT FloatComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,     BT uFloat64Complex,     BT uFloat64Complex,
192                                         BT DoubleComplex,       BT DoubleComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat128Complex,
193                                      BT uFloat128Complex,    BT uFloat128Complex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
194                                  },
195                                  {
196                /*      F */               BT Float,               BT Float,               BT Float,               BT Float,               BT Float,               BT Float,
197                                                 BT Float,               BT Float,               BT Float,               BT Float,               BT Float,               BT Float,
198                                                 BT Float,               BT Float,               BT Float,        BT FloatComplex,               BT Float,        BT FloatComplex,
199                                                 BT Float,        BT FloatComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
200                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
201                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
202                                  },
203                                  {
204                /*     FC */        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,
205                                          BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,
206                                          BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,        BT FloatComplex,
207                                          BT FloatComplex,        BT FloatComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,     BT uFloat64Complex,     BT uFloat64Complex,
208                                         BT DoubleComplex,       BT DoubleComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat128Complex,
209                                      BT uFloat128Complex,    BT uFloat128Complex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
210                                  },
211                                  {
212                /*    _FX */           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,
213                                             BT uFloat32x,           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,           BT uFloat32x,
214                                             BT uFloat32x,           BT uFloat32x,           BT uFloat32x,    BT uFloat32xComplex,           BT uFloat32x,    BT uFloat32xComplex,
215                                             BT uFloat32x,    BT uFloat32xComplex,           BT uFloat32x,    BT uFloat32xComplex,            BT uFloat64,     BT uFloat64Complex,
216                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
217                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
218                                  },
219                                  {
220                /*   _FXC */    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,
221                                      BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,
222                                      BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,
223                                      BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,    BT uFloat32xComplex,     BT uFloat64Complex,     BT uFloat64Complex,
224                                         BT DoubleComplex,       BT DoubleComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat128Complex,
225                                      BT uFloat128Complex,    BT uFloat128Complex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
226                                  },
227                                  {
228                /*     FD */            BT uFloat64,            BT uFloat64,            BT uFloat64,            BT uFloat64,            BT uFloat64,            BT uFloat64,
229                                              BT uFloat64,            BT uFloat64,            BT uFloat64,            BT uFloat64,            BT uFloat64,            BT uFloat64,
230                                              BT uFloat64,            BT uFloat64,            BT uFloat64,     BT uFloat64Complex,            BT uFloat64,     BT uFloat64Complex,
231                                              BT uFloat64,     BT uFloat64Complex,            BT uFloat64,     BT uFloat64Complex,            BT uFloat64,     BT uFloat64Complex,
232                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
233                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
234                                  },
235                                  {
236                /*   _FDC */     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,
237                                       BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,
238                                       BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,
239                                       BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,     BT uFloat64Complex,
240                                         BT DoubleComplex,       BT DoubleComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat128Complex,
241                                      BT uFloat128Complex,    BT uFloat128Complex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
242                                  },
243                                  {
244                /*      D */              BT Double,              BT Double,              BT Double,              BT Double,              BT Double,              BT Double,
245                                                BT Double,              BT Double,              BT Double,              BT Double,              BT Double,              BT Double,
246                                                BT Double,              BT Double,              BT Double,       BT DoubleComplex,              BT Double,       BT DoubleComplex,
247                                                BT Double,       BT DoubleComplex,              BT Double,       BT DoubleComplex,              BT Double,       BT DoubleComplex,
248                                                BT Double,       BT DoubleComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
249                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
250                                  },
251                                  {
252                /*     DC */       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,
253                                         BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,
254                                         BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,
255                                         BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,       BT DoubleComplex,
256                                         BT DoubleComplex,       BT DoubleComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat128Complex,
257                                      BT uFloat128Complex,    BT uFloat128Complex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
258                                  },
259                                  {
260                /*   F80X */           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,
261                                             BT uFloat64x,           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,           BT uFloat64x,
262                                             BT uFloat64x,           BT uFloat64x,           BT uFloat64x,    BT uFloat64xComplex,           BT uFloat64x,    BT uFloat64xComplex,
263                                             BT uFloat64x,    BT uFloat64xComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uFloat64x,    BT uFloat64xComplex,
264                                             BT uFloat64x,    BT uFloat64xComplex,           BT uFloat64x,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
265                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
266                                  },
267                                  {
268                /*  _FDXC */    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,
269                                      BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,
270                                      BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,
271                                      BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,
272                                      BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat64xComplex,    BT uFloat128Complex,
273                                      BT uFloat128Complex,    BT uFloat128Complex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
274                                  },
275                                  {
276                /*    F80 */           BT uuFloat80,           BT uuFloat80,           BT uuFloat80,           BT uuFloat80,           BT uuFloat80,           BT uuFloat80,
277                                             BT uuFloat80,           BT uuFloat80,           BT uuFloat80,           BT uuFloat80,           BT uuFloat80,           BT uuFloat80,
278                                             BT uuFloat80,           BT uuFloat80,           BT uuFloat80,    BT uFloat64xComplex,           BT uuFloat80,    BT uFloat64xComplex,
279                                             BT uuFloat80,    BT uFloat64xComplex,           BT uuFloat80,    BT uFloat64xComplex,           BT uuFloat80,    BT uFloat64xComplex,
280                                             BT uuFloat80,    BT uFloat64xComplex,           BT uuFloat80,    BT uFloat64xComplex,           BT uuFloat80,           BT uFloat128,
281                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
282                                  },
283                                  {
284                /*    _FB */           BT uFloat128,           BT uFloat128,           BT uFloat128,           BT uFloat128,           BT uFloat128,           BT uFloat128,
285                                             BT uFloat128,           BT uFloat128,           BT uFloat128,           BT uFloat128,           BT uFloat128,           BT uFloat128,
286                                             BT uFloat128,           BT uFloat128,           BT uFloat128,    BT uFloat128Complex,           BT uFloat128,    BT uFloat128Complex,
287                                             BT uFloat128,    BT uFloat128Complex,           BT uFloat128,    BT uFloat128Complex,           BT uFloat128,    BT uFloat128Complex,
288                                             BT uFloat128,    BT uFloat128Complex,           BT uFloat128,    BT uFloat128Complex,           BT uFloat128,           BT uFloat128,
289                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
290                                  },
291                                  {
292                /*  _FLDC */    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,
293                                      BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,
294                                      BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,
295                                      BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,
296                                      BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,    BT uFloat128Complex,
297                                      BT uFloat128Complex,    BT uFloat128Complex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
298                                  },
299                                  {
300                /*     FB */          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,
301                                            BT uuFloat128,          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,          BT uuFloat128,
302                                            BT uuFloat128,          BT uuFloat128,          BT uuFloat128,    BT uFloat128Complex,          BT uuFloat128,    BT uFloat128Complex,
303                                            BT uuFloat128,    BT uFloat128Complex,          BT uuFloat128,    BT uFloat128Complex,          BT uuFloat128,    BT uFloat128Complex,
304                                            BT uuFloat128,    BT uFloat128Complex,          BT uuFloat128,    BT uFloat128Complex,          BT uuFloat128,          BT uuFloat128,
305                                      BT uFloat128Complex,          BT uuFloat128,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
306                                  },
307                                  {
308                /*     LD */          BT LongDouble,          BT LongDouble,          BT LongDouble,          BT LongDouble,          BT LongDouble,          BT LongDouble,
309                                            BT LongDouble,          BT LongDouble,          BT LongDouble,          BT LongDouble,          BT LongDouble,          BT LongDouble,
310                                            BT LongDouble,          BT LongDouble,          BT LongDouble,   BT LongDoubleComplex,          BT LongDouble,   BT LongDoubleComplex,
311                                            BT LongDouble,   BT LongDoubleComplex,          BT LongDouble,   BT LongDoubleComplex,          BT LongDouble,   BT LongDoubleComplex,
312                                            BT LongDouble,   BT LongDoubleComplex,          BT LongDouble,   BT LongDoubleComplex,          BT LongDouble,          BT LongDouble,
313                                     BT LongDoubleComplex,          BT LongDouble,          BT LongDouble,   BT LongDoubleComplex,          BT uFloat128x,   BT uFloat128xComplex,
314                                  },
315                                  {
316                /*    LDC */   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,
317                                     BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,
318                                     BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,
319                                     BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,
320                                     BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,
321                                     BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT LongDoubleComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
322                                  },
323                                  {
324                /*   _FBX */          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,
325                                            BT uFloat128x,          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,          BT uFloat128x,
326                                            BT uFloat128x,          BT uFloat128x,          BT uFloat128x,   BT uFloat128xComplex,          BT uFloat128x,   BT uFloat128xComplex,
327                                            BT uFloat128x,   BT uFloat128xComplex,          BT uFloat128x,   BT uFloat128xComplex,          BT uFloat128x,   BT uFloat128xComplex,
328                                            BT uFloat128x,   BT uFloat128xComplex,          BT uFloat128x,   BT uFloat128xComplex,          BT uFloat128x,          BT uFloat128x,
329                                     BT uFloat128xComplex,          BT uFloat128x,          BT uFloat128x,   BT uFloat128xComplex,          BT uFloat128x,   BT uFloat128xComplex,
330                                  },
331                                  {
332                /* _FLDXC */   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
333                                     BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
334                                     BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
335                                     BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
336                                     BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
337                                     BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,   BT uFloat128xComplex,
338                                  },
339        }; // commonTypes
340        #undef BT
341        // GENERATED END
342        static_assert(
343                sizeof(commonTypes)/sizeof(commonTypes[0][0]) == ast::BasicKind::NUMBER_OF_BASIC_TYPES * ast::BasicKind::NUMBER_OF_BASIC_TYPES,
344                "Each basic type kind should have a corresponding row in the combined type matrix"
345        );
346
347class CommonType final : public ast::WithShortCircuiting {
348        const ast::Type * type2;
349        WidenMode widen;
350        ast::TypeEnvironment & tenv;
351        const ast::OpenVarSet & open;
352        ast::AssertionSet & need;
353        ast::AssertionSet & have;
354public:
355        static size_t traceId;
356        ast::ptr< ast::Type > result;
357
358        CommonType(
359                const ast::Type * t2, WidenMode w,
360                ast::TypeEnvironment & env, const ast::OpenVarSet & o,
361                ast::AssertionSet & need, ast::AssertionSet & have )
362        : type2( t2 ), widen( w ), tenv( env ), open( o ), need (need), have (have) ,result() {}
363
364        void previsit( const ast::Node * ) { visit_children = false; }
365
366        void postvisit( const ast::VoidType * ) {}
367
368        void postvisit( const ast::BasicType * basic ) {
369                if ( auto basic2 = dynamic_cast< const ast::BasicType * >( type2 ) ) {
370                        ast::BasicKind kind;
371                        if (basic->kind != basic2->kind && !widen.first && !widen.second) return;
372                        else if (!widen.first) kind = basic->kind; // widen.second
373                        else if (!widen.second) kind = basic2->kind;
374                        else kind = commonTypes[ basic->kind ][ basic2->kind ];
375                        // xxx - what does qualifiers even do here??
376                        if ( (basic->qualifiers >= basic2->qualifiers || widen.first)
377                                && (basic->qualifiers <= basic2->qualifiers || widen.second) ) {
378                                result = new ast::BasicType{ kind, basic->qualifiers | basic2->qualifiers };
379                        }
380                } else if (
381                        dynamic_cast< const ast::ZeroType * >( type2 )
382                        || dynamic_cast< const ast::OneType * >( type2 )
383                ) {
384                        if (widen.second) {
385                                result = new ast::BasicType{ basic->kind, basic->qualifiers | type2->qualifiers };
386                        }
387                } else if ( const ast::EnumInstType * enumInst = dynamic_cast< const ast::EnumInstType * >( type2 ) ) {
388                        const ast::EnumDecl* enumDecl = enumInst->base;
389                        if ( !enumDecl->base ) {
390                                ast::BasicKind kind = commonTypes[ basic->kind ][ ast::BasicKind::SignedInt ];
391                                if (
392                                        ( ( kind == basic->kind && basic->qualifiers >= type2->qualifiers )
393                                                || widen.first )
394                                        && ( ( kind != basic->kind && basic->qualifiers <= type2->qualifiers )
395                                                || widen.second )
396                                ) {
397                                        result = new ast::BasicType{ kind, basic->qualifiers | type2->qualifiers };
398                                }
399                        }
400                }
401        }
402
403private:
404        template< typename Pointer >
405        void getCommonWithVoidPointer( const Pointer * voidPtr, const Pointer * oPtr ) {
406                const ast::Type * base = oPtr->base;
407                if ( auto var = dynamic_cast< const ast::TypeInstType * >( base ) ) {
408                        auto entry = open.find( *var );
409                        if ( entry != open.end() ) {
410                                ast::AssertionSet need, have;
411                                if ( ! tenv.bindVar(
412                                        var, voidPtr->base, entry->second, need, have, open, widen )
413                                ) return;
414                        }
415                }
416                result = voidPtr;
417                add_qualifiers( result, oPtr->qualifiers );
418        }
419
420public:
421        void postvisit( const ast::PointerType * pointer ) {
422                if ( auto pointer2 = dynamic_cast< const ast::PointerType * >( type2 ) ) {
423                        if (
424                                widen.first
425                                && pointer2->base.as< ast::VoidType >()
426                                && ! ast::isFtype( pointer->base )
427                        ) {
428                                getCommonWithVoidPointer( pointer2, pointer );
429                        } else if (
430                                widen.second
431                                && pointer->base.as< ast::VoidType >()
432                                && ! ast::isFtype( pointer2->base )
433                        ) {
434                                getCommonWithVoidPointer( pointer, pointer2 );
435                        } else if (
436                                ( pointer->base->qualifiers >= pointer2->base->qualifiers || widen.first )
437                                && ( pointer->base->qualifiers <= pointer2->base->qualifiers || widen.second )
438                        ) {
439                                ast::CV::Qualifiers q1 = pointer->base->qualifiers;
440                                ast::CV::Qualifiers q2 = pointer2->base->qualifiers;
441
442                                // force t{1,2} to be cloned if their qualifiers must be stripped, so that
443                                // pointer{,2}->base are unchanged
444                                ast::ptr< ast::Type > t1{ pointer->base }, t2{ pointer2->base };
445                                reset_qualifiers( t1 );
446                                reset_qualifiers( t2 );
447
448                                ast::OpenVarSet newOpen{ open };
449                                if ( unifyExact( t1, t2, tenv, have, need, newOpen, noWiden() ) ) {
450                                        result = pointer;
451                                        if ( q1.val != q2.val ) {
452                                                // reset result->base->qualifiers to be union of two base qualifiers
453                                                strict_dynamic_cast< ast::PointerType * >(
454                                                        result.get_and_mutate()
455                                                )->base.get_and_mutate()->qualifiers = q1 | q2;
456                                        }
457                                } else if ( isFtype (t1) && isFtype (t2) ) {
458                                        auto f1 = t1.as<ast::FunctionType>();
459                                        if (!f1) return;
460                                        auto f2 = t2.strict_as<ast::FunctionType>();
461
462                                        assertf(f1->returns.size() <= 1, "Function return should not be a list");
463                                        assertf(f2->returns.size() <= 1, "Function return should not be a list");
464
465                                        if (
466                                                ( f1->params.size() != f2->params.size() || f1->returns.size() != f2->returns.size() )
467                                                && ! f1->isTtype()
468                                                && ! f2->isTtype()
469                                        ) return;
470
471                                        auto params1 = flattenList( f1->params, tenv );
472                                        auto params2 = flattenList( f2->params, tenv );
473
474                                        auto crnt1 = params1.begin();
475                                        auto crnt2 = params2.begin();
476                                        auto end1 = params1.end();
477                                        auto end2 = params2.end();
478
479                                        while (crnt1 != end1 && crnt2 != end2 ) {
480                                                const ast::Type * arg1 = *crnt1;
481                                                const ast::Type * arg2 = *crnt2;
482
483                                                bool isTuple1 = Tuples::isTtype( t1 );
484                                                bool isTuple2 = Tuples::isTtype( t2 );
485
486                                                // assumes here that ttype *must* be last parameter
487                                                if ( isTuple1 && ! isTuple2 ) {
488                                                        // combine remainder of list2, then unify
489                                                        if (unifyExact(
490                                                                arg1, tupleFromTypes( crnt2, end2 ), tenv, need, have, open,
491                                                                noWiden() )) {
492                                                                        break;
493                                                        } else return;
494                                                } else if ( ! isTuple1 && isTuple2 ) {
495                                                        // combine remainder of list1, then unify
496                                                        if (unifyExact(
497                                                                tupleFromTypes( crnt1, end1 ), arg2, tenv, need, have, open,
498                                                                noWiden() )) {
499                                                                        break;
500                                                        } else return;
501                                                }
502
503                                                // allow qualifiers of pointer and reference base to become more specific
504                                                if (auto ref1 = dynamic_cast<const ast::ReferenceType *> (arg1)) {
505                                                        if (auto ref2 = dynamic_cast<const ast::ReferenceType *> (arg2)) {
506                                                                ast::ptr<ast::Type> base1 = ref1->base;
507                                                                ast::ptr<ast::Type> base2 = ref2->base;
508
509                                                                // xxx - assume LHS is always the target type
510
511                                                                if ( ! ((widen.second && ref2->qualifiers.is_mutex)
512                                                                || (ref1->qualifiers.is_mutex == ref2->qualifiers.is_mutex ))) return;
513
514                                                                if ( (widen.second && base1->qualifiers <= base2->qualifiers ) || (base2->qualifiers == base1->qualifiers) ) {
515
516                                                                        reset_qualifiers(base1);
517                                                                        reset_qualifiers(base2);
518
519                                                                        if ( !unifyExact(
520                                                                                base1, base2, tenv, need, have, open, noWiden() )
521                                                                        ) return;
522                                                                }
523                                                        } else return;
524                                                } else if (auto ptr1 = dynamic_cast<const ast::PointerType *> (arg1)) {
525                                                        if (auto ptr2 = dynamic_cast<const ast::PointerType *> (arg2)) {
526                                                                ast::ptr<ast::Type> base1 = ptr1->base;
527                                                                ast::ptr<ast::Type> base2 = ptr2->base;
528
529                                                                // xxx - assume LHS is always the target type
530                                                                // a function accepting const can always be called by non-const arg
531
532                                                                if ( (widen.second && base1->qualifiers <= base2->qualifiers ) || (base2->qualifiers == base1->qualifiers) ) {
533
534                                                                        reset_qualifiers(base1);
535                                                                        reset_qualifiers(base2);
536
537                                                                        if ( ! unifyExact(
538                                                                                base1, base2, tenv, need, have, open, noWiden() )
539                                                                        ) return;
540                                                                }
541                                                        } else return;
542                                                } else if (! unifyExact(
543                                                                arg1, arg2, tenv, need, have, open, noWiden() )) {
544                                                        return;
545                                                }
546                                                ++crnt1; ++crnt2;
547                                        }
548                                        if ( crnt1 != end1 ) {
549                                                // try unifying empty tuple with ttype
550                                                const ast::Type * t1 = *crnt1;
551                                                if (! Tuples::isTtype( t1 ) ) return;
552                                                if (! unifyExact(
553                                                        t1, tupleFromTypes( crnt2, end2 ), tenv, need, have, open,
554                                                        noWiden() )) return;
555                                        } else if ( crnt2 != end2 ) {
556                                                // try unifying empty tuple with ttype
557                                                const ast::Type * t2 = *crnt2;
558                                                if ( !Tuples::isTtype( t2 ) ) return;
559                                                if ( !unifyExact(
560                                                        tupleFromTypes( crnt1, end1 ), t2, tenv, need, have, open,
561                                                        noWiden() )) return;
562                                        }
563                                        if ((f1->returns.size() == 0 && f2->returns.size() == 0)
564                                          || (f1->returns.size() == 1 && f2->returns.size() == 1 && unifyExact(f1->returns[0], f2->returns[0], tenv, need, have, open, noWiden()))) {
565                                                result = pointer;
566
567                                                for (auto & assn : f1->assertions) {
568                                                        auto i = need.find(assn);
569                                                        if (i != need.end()) i->second.isUsed = true;
570                                                        auto j = have.find(assn);
571                                                        if (j != have.end()) j->second.isUsed = true;
572                                                }
573
574                                                for (auto & assn : f2->assertions) {
575                                                        auto i = need.find(assn);
576                                                        if (i != need.end()) i->second.isUsed = true;
577                                                        auto j = have.find(assn);
578                                                        if (j != have.end()) j->second.isUsed = true;
579                                                }
580                                        }
581                                } // if ftype
582                        }
583                } else if ( widen.second && dynamic_cast< const ast::ZeroType * >( type2 ) ) {
584                        result = pointer;
585                        add_qualifiers( result, type2->qualifiers );
586                }
587        }
588
589        void postvisit( const ast::ArrayType * ) {}
590
591        void postvisit( const ast::ReferenceType * ref ) {
592                if ( auto ref2 = dynamic_cast< const ast::ReferenceType * >( type2 ) ) {
593                        if (
594                                widen.first && ref2->base.as< ast::VoidType >() && ! ast::isFtype( ref->base )
595                        ) {
596                                getCommonWithVoidPointer( ref2, ref );
597                        } else if (
598                                widen.second && ref->base.as< ast::VoidType>() && ! ast::isFtype( ref2->base )
599                        ) {
600                                getCommonWithVoidPointer( ref, ref2 );
601                        } else if (
602                                ( ref->base->qualifiers >= ref2->base->qualifiers || widen.first )
603                                && ( ref->base->qualifiers <= ref2->base->qualifiers || widen.second )
604                        ) {
605                                ast::CV::Qualifiers q1 = ref->base->qualifiers, q2 = ref2->base->qualifiers;
606
607                                // force t{1,2} to be cloned if their qualifiers must be stripped, so that
608                                // ref{,2}->base are unchanged
609                                ast::ptr< ast::Type > t1{ ref->base }, t2{ ref2->base };
610                                reset_qualifiers( t1 );
611                                reset_qualifiers( t2 );
612
613                                ast::OpenVarSet newOpen{ open };
614                                if ( unifyExact( t1, t2, tenv, have, need, newOpen, noWiden() ) ) {
615                                        result = ref;
616                                        if ( q1.val != q2.val ) {
617                                                // reset result->base->qualifiers to be union of two base qualifiers
618                                                strict_dynamic_cast< ast::ReferenceType * >(
619                                                        result.get_and_mutate()
620                                                )->base.get_and_mutate()->qualifiers = q1 | q2;
621                                        }
622                                }
623                        }
624                } else if ( widen.second && dynamic_cast< const ast::ZeroType * >( type2 ) ) {
625                        result = ref;
626                        add_qualifiers( result, type2->qualifiers );
627                } else {
628                        if (!dynamic_cast<const ast::EnumInstType *>(type2))
629                                result = commonType( type2, ref, tenv, need, have, open, widen );
630                }
631        }
632
633        void postvisit( const ast::FunctionType * ) {}
634
635        void postvisit( const ast::StructInstType * ) {}
636
637        void postvisit( const ast::UnionInstType * ) {}
638
639        void postvisit( const ast::EnumInstType * enumInst ) {
640                if ( enumInst->base && !enumInst->base->isTyped ) {
641                        auto basicType = new ast::BasicType( ast::BasicKind::UnsignedInt );
642                        result = commonType( basicType, type2, tenv, need, have, open, widen);
643                }
644        }
645
646        void postvisit( const ast::TraitInstType * ) {}
647
648        void postvisit( const ast::TypeInstType * ) {}
649
650        void postvisit( const ast::TupleType * ) {}
651
652        void postvisit( const ast::VarArgsType * ) {}
653
654        void postvisit( const ast::ZeroType * zero ) {
655                if ( !widen.first ) return;
656                if ( dynamic_cast< const ast::BasicType * >( type2 )
657                                || dynamic_cast< const ast::PointerType * >( type2 ) ) {
658                        if ( widen.second || zero->qualifiers <= type2->qualifiers ) {
659                                result = type2;
660                                add_qualifiers( result, zero->qualifiers );
661                        }
662                } else if ( widen.second && dynamic_cast< const ast::OneType * >( type2 ) ) {
663                        result = new ast::BasicType{
664                                ast::BasicKind::SignedInt, zero->qualifiers | type2->qualifiers };
665                } else if ( const ast::EnumInstType * enumInst = dynamic_cast< const ast::EnumInstType * >( type2 ) ) {
666                        const ast::EnumDecl * enumDecl = enumInst->base;
667                        if ( !enumDecl->base ) {
668                                if ( widen.second || zero->qualifiers <= type2->qualifiers ) {
669                                        result = type2;
670                                        add_qualifiers( result, zero->qualifiers );
671                                }
672                        }
673                }
674        }
675
676        void postvisit( const ast::OneType * one ) {
677                if ( !widen.first ) return;
678                if ( dynamic_cast< const ast::BasicType * >( type2 ) ) {
679                        if ( widen.second || one->qualifiers <= type2->qualifiers ) {
680                                result = type2;
681                                add_qualifiers( result, one->qualifiers );
682                        }
683                } else if ( widen.second && dynamic_cast< const ast::ZeroType * >( type2 ) ) {
684                        result = new ast::BasicType{
685                                ast::BasicKind::SignedInt, one->qualifiers | type2->qualifiers };
686                } else if ( const ast::EnumInstType * enumInst = dynamic_cast< const ast::EnumInstType * >( type2 ) ) {
687                        const ast::EnumDecl * enumDecl = enumInst->base;
688                        if ( !enumDecl->base ) {
689                                if ( widen.second || one->qualifiers <= type2->qualifiers ) {
690                                        result = type2;
691                                        add_qualifiers( result, one->qualifiers );
692                                }
693                        }
694                }
695        }
696};
697
698// size_t CommonType::traceId = Stats::Heap::new_stacktrace_id("CommonType");
699
700ast::ptr< ast::Type > handleReference(
701        const ast::ptr< ast::Type > & t1, const ast::ptr< ast::Type > & t2, WidenMode widen,
702        ast::TypeEnvironment & env,
703        const ast::OpenVarSet & open
704) {
705        ast::ptr<ast::Type> common;
706        ast::AssertionSet have, need;
707        ast::OpenVarSet newOpen( open );
708
709        // need unify to bind type variables
710        if ( unify( t1, t2, env, have, need, newOpen, common ) ) {
711                ast::CV::Qualifiers q1 = t1->qualifiers, q2 = t2->qualifiers;
712                PRINT(
713                        std::cerr << "unify success: " << widenFirst << " " << widenSecond << std::endl;
714                )
715                if ( ( widen.first || q2 <= q1 ) && ( widen.second || q1 <= q2 ) ) {
716                        PRINT(
717                                std::cerr << "widen okay" << std::endl;
718                        )
719                        add_qualifiers( common, q1 | q2 );
720                        return common;
721                }
722        }
723
724        PRINT(
725                std::cerr << "exact unify failed: " << t1 << " " << t2 << std::endl;
726        )
727        return { nullptr };
728}
729
730} // namespace
731
732ast::ptr< ast::Type > commonType(
733        const ast::ptr< ast::Type > & type1, const ast::ptr< ast::Type > & type2,
734        ast::TypeEnvironment & env, ast::AssertionSet & need, ast::AssertionSet & have,
735        const ast::OpenVarSet & open, WidenMode widen
736) {
737        unsigned depth1 = type1->referenceDepth();
738        unsigned depth2 = type2->referenceDepth();
739
740        if ( depth1 != depth2 ) {  // implies depth1 > 0 || depth2 > 0
741                PRINT(
742                        std::cerr << "reference depth diff: " << (depth1-depth2) << std::endl;
743                )
744                ast::ptr< ast::Type > result;
745                const ast::ReferenceType * ref1 = type1.as< ast::ReferenceType >();
746                const ast::ReferenceType * ref2 = type2.as< ast::ReferenceType >();
747
748                if ( depth1 > depth2 ) {
749                        assert( ref1 );
750                        result = handleReference( ref1->base, type2, widen, env, open );
751                } else {  // Implies depth1 < depth2
752                        assert( ref2 );
753                        result = handleReference( type1, ref2->base, widen, env, open );
754                }
755
756                if ( result && ref1 ) {
757                        // formal is reference, so result should be reference
758                        PRINT(
759                                std::cerr << "formal is reference; result should be reference" << std::endl;
760                        )
761                        result = new ast::ReferenceType{ result, ref1->qualifiers };
762                }
763
764                PRINT(
765                        std::cerr << "common type of reference [" << type1 << "] and [" << type2 << "] is "
766                        "[" << result << "]" << std::endl;
767                )
768                return result;
769        }
770        // otherwise both are reference types of the same depth and this is handled by the visitor
771        return ast::Pass<CommonType>::read( type1.get(),
772                type2, widen, env, open, need, have );
773}
774
775} // namespace ResolvExpr
776
777// Local Variables: //
778// tab-width: 4 //
779// mode: c++ //
780// compile-command: "make install" //
781// End: //
Note: See TracBrowser for help on using the repository browser.