00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040 #ifdef USE_PCH
00041 #include "common_com_pch.h"
00042 #endif
00043 #pragma hdrstop
00044 #include "defs.h"
00045 #include "wn.h"
00046 #include "wn_util.h"
00047
00048 #include "f90_utils.h"
00049
00050
00051
00052
00053
00054 BOOL F90_Is_Transformational(INT32 intrinsic)
00055 {
00056 switch (intrinsic) {
00057 case INTRN_MATMUL:
00058 case INTRN_SPREAD:
00059 case INTRN_RESHAPE:
00060 case INTRN_TRANSPOSE:
00061 case INTRN_ALL:
00062 case INTRN_ANY:
00063 case INTRN_COUNT:
00064 case INTRN_PRODUCT:
00065 case INTRN_SUM:
00066 case INTRN_EOSHIFT:
00067 case INTRN_MAXVAL:
00068 case INTRN_MINVAL:
00069 case INTRN_MAXLOC:
00070 case INTRN_MINLOC:
00071 case INTRN_CSHIFT:
00072 case INTRN_DOT_PRODUCT:
00073 case INTRN_PACK:
00074 case INTRN_UNPACK:
00075 return(TRUE);
00076 default:
00077 return (FALSE);
00078 }
00079 }
00080
00081
00082
00083 BOOL F90_Is_Char_Intrinsic(INT32 intr)
00084 {
00085 switch(intr) {
00086 case INTRN_CASSIGNSTMT:
00087 case INTRN_CONCATEXPR:
00088 case INTRN_ADJUSTL:
00089 case INTRN_ADJUSTR:
00090 case INTRN_CEQEXPR:
00091 case INTRN_CNEEXPR:
00092 case INTRN_CGEEXPR:
00093 case INTRN_CGTEXPR:
00094 case INTRN_CLEEXPR:
00095 case INTRN_CLTEXPR:
00096 case INTRN_I4CLEN:
00097 case INTRN_I4CINDEX:
00098 case INTRN_CLGE:
00099 case INTRN_CLGT:
00100 case INTRN_CLLE:
00101 case INTRN_CLLT:
00102 case INTRN_LENTRIM:
00103 case INTRN_F90INDEX:
00104 case INTRN_SCAN:
00105 case INTRN_VERIFY:
00106 return (TRUE);
00107 default:
00108 return (FALSE);
00109 }
00110 }
00111
00112
00113
00114
00115
00116
00117
00118
00119
00120 INT F90_Get_Dim(WN *dim_wn)
00121 {
00122 OPERATOR opr;
00123 opr = WN_operator(dim_wn);
00124 if (WN_opcode(dim_wn) == OPC_VPARM) {
00125 return (0);
00126 } else if (opr == OPR_PARM) {
00127 return (F90_Get_Dim(WN_kid0(dim_wn)));
00128 } else if (opr == OPR_INTCONST) {
00129 return (WN_const_val(dim_wn));
00130 } else {
00131 return (0);
00132 }
00133 }
00134
00135
00136
00137
00138
00139
00140
00141
00142
00143
00144
00145
00146
00147
00148 BOOL F90_Size_Walk(WN *expr, INT *ndim, WN **sizes)
00149 {
00150 WN *temp;
00151 WN *temp_sizes[MAX_NDIM];
00152 INT child_ndim;
00153 INT i,j,dim,numkids;
00154 BOOL sized;
00155
00156 *ndim = 0;
00157 sized = FALSE;
00158
00159 switch (WN_operator(expr)) {
00160 case OPR_COMMA:
00161
00162 temp = WN_first(WN_kid0(expr));
00163 while (temp) {
00164 sized = F90_Size_Walk(temp,ndim,sizes);
00165 if (sized) return (TRUE);
00166 temp = WN_next(temp);
00167 }
00168 return (FALSE);
00169
00170 case OPR_RCOMMA:
00171
00172 temp = WN_first(WN_kid1(expr));
00173 while (temp) {
00174 sized = F90_Size_Walk(temp,ndim,sizes);
00175 if (sized) return (TRUE);
00176 temp = WN_next(temp);
00177 }
00178 return (FALSE);
00179
00180 case OPR_ARRAYEXP:
00181 numkids = WN_kid_count(expr);
00182 if (numkids != 1) {
00183 *ndim = numkids-1;
00184 for (i = 1; i < numkids; i++) {
00185 sizes[i-1] = WN_COPY_Tree(WN_kid(expr,i));
00186 }
00187 return (TRUE);
00188 }
00189
00190 break;
00191
00192 case OPR_ARRSECTION:
00193 numkids = (WN_kid_count(expr) - 1)/2;
00194 j = 0;
00195 for (i = 1; i <= numkids; i++) {
00196 if (F90_Size_Walk(WN_kid(expr,i+numkids),&child_ndim,temp_sizes)) {
00197 sizes[j] = temp_sizes[0];
00198 j += 1;
00199 }
00200 }
00201 *ndim = j;
00202 return (j != 0);
00203
00204 case OPR_TRIPLET:
00205 *ndim = 1;
00206 sizes[0] = WN_COPY_Tree(WN_kid2(expr));
00207 return (TRUE);
00208
00209 case OPR_INTRINSIC_OP:
00210 switch (WN_intrinsic(expr)) {
00211 case INTRN_SPREAD:
00212 sized = F90_Size_Walk(WN_kid0(expr),&child_ndim,temp_sizes);
00213 if (!sized) {
00214
00215 child_ndim = 0;
00216 }
00217 dim = child_ndim - F90_Get_Dim(WN_kid1(expr)) + 1;
00218 for (i=0,j=0; i <= child_ndim; i++) {
00219 if (i == dim) {
00220 sizes[i] = WN_COPY_Tree(WN_kid0(WN_kid2(expr)));
00221 } else {
00222 sizes[i] = temp_sizes[j++];
00223 }
00224 }
00225 *ndim = child_ndim + 1;
00226 return (TRUE);
00227
00228 case INTRN_TRANSPOSE:
00229 (void) F90_Size_Walk(WN_kid0(expr),ndim,sizes);
00230 temp = sizes[0];
00231 sizes[0] = sizes[1];
00232 sizes[1] = temp;
00233 return (TRUE);
00234
00235
00236 case INTRN_MATMUL:
00237 {
00238 INT dim1,dim2;
00239 WN *size1[2],*size2[2];
00240 F90_Size_Walk(WN_kid0(expr),&dim1,size1);
00241 F90_Size_Walk(WN_kid1(expr),&dim2,size2);
00242
00243 if (dim1 == 1) {
00244
00245 *ndim = 1;
00246 sizes[0] = size2[0];
00247 WN_DELETE_Tree(size1[0]);
00248 WN_DELETE_Tree(size2[1]);
00249 } else if (dim2 == 1) {
00250
00251 *ndim = 1;
00252 sizes[0] = size1[1];
00253 WN_DELETE_Tree(size1[0]);
00254 WN_DELETE_Tree(size2[0]);
00255 } else {
00256 Is_True(dim1==2 && dim2 == 2,("Bad MATMUL"));
00257
00258 *ndim = 2;
00259 sizes[1] = size1[1];
00260 sizes[0] = size2[0];
00261 WN_DELETE_Tree(size1[0]);
00262 WN_DELETE_Tree(size2[1]);
00263 }
00264 return (TRUE);
00265 }
00266
00267 case INTRN_ALL:
00268 case INTRN_ANY:
00269 case INTRN_COUNT:
00270 case INTRN_PRODUCT:
00271 case INTRN_SUM:
00272 case INTRN_MAXVAL:
00273 case INTRN_MINVAL:
00274 temp = WN_kid1(expr);
00275 dim = F90_Get_Dim(WN_kid1(expr));
00276 if (dim==0) {
00277
00278 *ndim = 0;
00279 return (FALSE);
00280 } else {
00281 sized = F90_Size_Walk(WN_kid0(expr),&child_ndim,temp_sizes);
00282 if (dim == 1 && child_ndim == 1) {
00283
00284 *ndim = 0;
00285 } else {
00286 dim = child_ndim - dim;
00287 for (i=0,j=0; i < child_ndim; i++) {
00288 if (i != dim) {
00289 sizes[j++] = temp_sizes[i];
00290 } else {
00291 WN_DELETE_Tree(temp_sizes[i]);
00292 }
00293 }
00294 *ndim = child_ndim - 1;
00295 }
00296 return (*ndim != 0);
00297 }
00298
00299
00300 case INTRN_MAXLOC:
00301 case INTRN_MINLOC:
00302 temp = WN_kid1(expr);
00303 dim = F90_Get_Dim(WN_kid1(expr));
00304 if (dim==0) {
00305
00306 *ndim = 1;
00307 (void) F90_Size_Walk(WN_kid0(expr),&child_ndim,temp_sizes);
00308 sizes[0] = WN_Intconst(MTYPE_I4,child_ndim);
00309 return (TRUE);
00310 } else {
00311 sized = F90_Size_Walk(WN_kid0(expr),&child_ndim,temp_sizes);
00312 dim = child_ndim - dim;
00313 for (i=0,j=0; i < child_ndim; i++) {
00314 if (i != dim) {
00315 sizes[j++] = temp_sizes[i];
00316 } else {
00317 WN_DELETE_Tree(temp_sizes[i]);
00318 }
00319 }
00320 *ndim = child_ndim - 1;
00321 return (*ndim != 0);
00322 }
00323
00324 case INTRN_EOSHIFT:
00325 case INTRN_CSHIFT:
00326 return (F90_Size_Walk(WN_kid0(expr),ndim,sizes));
00327
00328 case INTRN_PACK:
00329
00330 return (F90_Size_Walk(WN_kid2(expr),ndim,sizes));
00331
00332 case INTRN_UNPACK:
00333 return (F90_Size_Walk(WN_kid1(expr),ndim,sizes));
00334
00335 default:
00336 break;
00337 }
00338 default:
00339 break;
00340 }
00341
00342
00343 sized = FALSE;
00344 numkids = WN_kid_count(expr);
00345 for (i=0; i < numkids; i++) {
00346 sized = F90_Size_Walk(WN_kid(expr,i),ndim,sizes);
00347 if (sized) break;
00348 }
00349 return (sized);
00350 }
00351
00352
00353
00354
00355
00356
00357
00358
00359
00360 INT F90_Rank_Walk(WN * tree)
00361 {
00362 INT rank;
00363 INT i;
00364 WN *temp_sizes[MAX_NDIM];
00365 (void) F90_Size_Walk(tree,&rank,temp_sizes);
00366
00367 for (i=0; i < rank; i++) {
00368 WN_DELETE_Tree(temp_sizes[i]);
00369 }
00370
00371 return(rank);
00372 }
00373
00374
00375
00376
00377
00378
00379
00380
00381
00382
00383
00384
00385 WN * F90_Wrap_ARREXP(WN * expr)
00386 {
00387 WN * r;
00388 INT i;
00389 INT ndim;
00390 WN *sizes[MAX_NDIM];
00391 BOOL is_array_valued;
00392 TYPE_ID ty;
00393
00394 if (WN_operator(expr) == OPR_TRIPLET) {
00395
00396 return (expr);
00397 }
00398 is_array_valued = F90_Size_Walk(expr, &ndim, sizes);
00399 if (is_array_valued) {
00400 ty = WN_rtype(expr);
00401 switch (ty) {
00402 case MTYPE_I1:
00403 case MTYPE_I2:
00404 case MTYPE_B:
00405 ty = MTYPE_I4;
00406 break;
00407 case MTYPE_U1:
00408 case MTYPE_U2:
00409 ty = MTYPE_U4;
00410 break;
00411 default:
00412 break;
00413 }
00414 r = WN_Create(OPCODE_make_op(OPR_ARRAYEXP,ty,MTYPE_V),
00415 ndim+1);
00416 WN_kid0(r) = expr;
00417 for (i=0; i<ndim; i++) {
00418 WN_kid(r,i+1) = sizes[i];
00419 }
00420 } else {
00421 r = expr;
00422 }
00423 return (r);
00424 }
00425
00426
00427
00428
00429
00430
00431
00432
00433
00434
00435
00436 WN *
00437 F90_wrap_cvtl(WN * wn, TYPE_ID ty)
00438 {
00439 WN *r;
00440
00441 switch (ty) {
00442 case MTYPE_I1:
00443 r = WN_CreateCvtl(OPC_I4CVTL,8,wn);
00444 break;
00445 case MTYPE_I2:
00446 r = WN_CreateCvtl(OPC_I4CVTL,16,wn);
00447 break;
00448 case MTYPE_U1:
00449 r = WN_CreateCvtl(OPC_U4CVTL,8,wn);
00450 break;
00451 case MTYPE_U2:
00452 r = WN_CreateCvtl(OPC_U4CVTL,16,wn);
00453 break;
00454 default:
00455 r = wn;
00456 }
00457
00458 return (r);
00459 }