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 #include "config.h"
00030 #include "system.h"
00031 #include "toplev.h"
00032 #include "flags.h"
00033 #ifdef SGI_MONGOOSE
00034
00035 #include "rtl.h"
00036 #endif
00037 #include "tree.h"
00038 #include "c-tree.h"
00039
00040 enum formals_style_enum {
00041 ansi,
00042 k_and_r_names,
00043 k_and_r_decls
00044 };
00045 typedef enum formals_style_enum formals_style;
00046
00047
00048 static const char *data_type;
00049
00050 static char *affix_data_type PARAMS ((const char *)) ATTRIBUTE_MALLOC;
00051 static const char *gen_formal_list_for_type PARAMS ((tree, formals_style));
00052 static int deserves_ellipsis PARAMS ((tree));
00053 static const char *gen_formal_list_for_func_def PARAMS ((tree, formals_style));
00054 static const char *gen_type PARAMS ((const char *, tree, formals_style));
00055 static const char *gen_decl PARAMS ((tree, int, formals_style));
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071 static char *
00072 affix_data_type (param)
00073 const char *param;
00074 {
00075 char *const type_or_decl = ASTRDUP (param);
00076 char *p = type_or_decl;
00077 char *qualifiers_then_data_type;
00078 char saved;
00079
00080
00081
00082 for (;;)
00083 {
00084 if (!strncmp (p, "volatile ", 9))
00085 {
00086 p += 9;
00087 continue;
00088 }
00089 if (!strncmp (p, "const ", 6))
00090 {
00091 p += 6;
00092 continue;
00093 }
00094 break;
00095 }
00096
00097
00098
00099
00100 if (p == type_or_decl)
00101 return concat (data_type, " ", type_or_decl, NULL);
00102
00103 saved = *p;
00104 *p = '\0';
00105 qualifiers_then_data_type = concat (type_or_decl, data_type, NULL);
00106 *p = saved;
00107 return reconcat (qualifiers_then_data_type,
00108 qualifiers_then_data_type, " ", p, NULL);
00109 }
00110
00111
00112
00113
00114
00115
00116
00117
00118 static const char *
00119 gen_formal_list_for_type (fntype, style)
00120 tree fntype;
00121 formals_style style;
00122 {
00123 const char *formal_list = "";
00124 tree formal_type;
00125
00126 if (style != ansi)
00127 return "()";
00128
00129 formal_type = TYPE_ARG_TYPES (fntype);
00130 while (formal_type && TREE_VALUE (formal_type) != void_type_node)
00131 {
00132 const char *this_type;
00133
00134 if (*formal_list)
00135 formal_list = concat (formal_list, ", ", NULL);
00136
00137 this_type = gen_type ("", TREE_VALUE (formal_type), ansi);
00138 formal_list
00139 = ((strlen (this_type))
00140 ? concat (formal_list, affix_data_type (this_type), NULL)
00141 : concat (formal_list, data_type, NULL));
00142
00143 formal_type = TREE_CHAIN (formal_type);
00144 }
00145
00146
00147
00148
00149
00150
00151
00152
00153
00154
00155
00156
00157
00158
00159
00160
00161
00162
00163
00164
00165
00166
00167
00168
00169
00170
00171
00172
00173
00174
00175
00176 if (!*formal_list)
00177 {
00178 if (TYPE_ARG_TYPES (fntype))
00179
00180 formal_list = "void";
00181 else
00182 formal_list = "/* ??? */";
00183 }
00184 else
00185 {
00186
00187
00188
00189 if (!formal_type)
00190 formal_list = concat (formal_list, ", ...", NULL);
00191 }
00192
00193 return concat (" (", formal_list, ")", NULL);
00194 }
00195
00196
00197
00198
00199
00200
00201
00202 static int
00203 deserves_ellipsis (fntype)
00204 tree fntype;
00205 {
00206 tree formal_type;
00207
00208 formal_type = TYPE_ARG_TYPES (fntype);
00209 while (formal_type && TREE_VALUE (formal_type) != void_type_node)
00210 formal_type = TREE_CHAIN (formal_type);
00211
00212
00213
00214
00215
00216 return (!formal_type && TYPE_ARG_TYPES (fntype));
00217 }
00218
00219
00220
00221
00222
00223
00224
00225
00226
00227
00228
00229
00230
00231
00232
00233
00234
00235
00236
00237
00238 static const char *
00239 gen_formal_list_for_func_def (fndecl, style)
00240 tree fndecl;
00241 formals_style style;
00242 {
00243 const char *formal_list = "";
00244 tree formal_decl;
00245
00246 formal_decl = DECL_ARGUMENTS (fndecl);
00247 while (formal_decl)
00248 {
00249 const char *this_formal;
00250
00251 if (*formal_list && ((style == ansi) || (style == k_and_r_names)))
00252 formal_list = concat (formal_list, ", ", NULL);
00253 this_formal = gen_decl (formal_decl, 0, style);
00254 if (style == k_and_r_decls)
00255 formal_list = concat (formal_list, this_formal, "; ", NULL);
00256 else
00257 formal_list = concat (formal_list, this_formal, NULL);
00258 formal_decl = TREE_CHAIN (formal_decl);
00259 }
00260 if (style == ansi)
00261 {
00262 if (!DECL_ARGUMENTS (fndecl))
00263 formal_list = concat (formal_list, "void", NULL);
00264 if (deserves_ellipsis (TREE_TYPE (fndecl)))
00265 formal_list = concat (formal_list, ", ...", NULL);
00266 }
00267 if ((style == ansi) || (style == k_and_r_names))
00268 formal_list = concat (" (", formal_list, ")", NULL);
00269 return formal_list;
00270 }
00271
00272
00273
00274
00275
00276
00277
00278
00279
00280
00281
00282
00283
00284
00285
00286
00287
00288
00289
00290
00291
00292
00293
00294
00295
00296
00297
00298
00299
00300
00301
00302
00303
00304
00305
00306
00307
00308
00309
00310
00311
00312
00313 static const char *
00314 gen_type (ret_val, t, style)
00315 const char *ret_val;
00316 tree t;
00317 formals_style style;
00318 {
00319 tree chain_p;
00320
00321
00322 if (TYPE_NAME (t) && TREE_CODE (TYPE_NAME (t)) == TYPE_DECL)
00323 data_type = IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (t)));
00324 else
00325 {
00326 switch (TREE_CODE (t))
00327 {
00328 case POINTER_TYPE:
00329 if (TYPE_READONLY (t))
00330 ret_val = concat ("const ", ret_val, NULL);
00331 if (TYPE_VOLATILE (t))
00332 ret_val = concat ("volatile ", ret_val, NULL);
00333
00334 ret_val = concat ("*", ret_val, NULL);
00335
00336 if (TREE_CODE (TREE_TYPE (t)) == ARRAY_TYPE || TREE_CODE (TREE_TYPE (t)) == FUNCTION_TYPE)
00337 ret_val = concat ("(", ret_val, ")", NULL);
00338
00339 ret_val = gen_type (ret_val, TREE_TYPE (t), style);
00340
00341 return ret_val;
00342
00343 case ARRAY_TYPE:
00344 if (!COMPLETE_TYPE_P (t) || TREE_CODE (TYPE_SIZE (t)) != INTEGER_CST)
00345 ret_val = gen_type (concat (ret_val, "[]", NULL),
00346 TREE_TYPE (t), style);
00347 else if (int_size_in_bytes (t) == 0)
00348 ret_val = gen_type (concat (ret_val, "[0]", NULL),
00349 TREE_TYPE (t), style);
00350 else
00351 {
00352 int size = (int_size_in_bytes (t) / int_size_in_bytes (TREE_TYPE (t)));
00353 char buff[10];
00354 sprintf (buff, "[%d]", size);
00355 ret_val = gen_type (concat (ret_val, buff, NULL),
00356 TREE_TYPE (t), style);
00357 }
00358 break;
00359
00360 case FUNCTION_TYPE:
00361 ret_val = gen_type (concat (ret_val,
00362 gen_formal_list_for_type (t, style),
00363 NULL),
00364 TREE_TYPE (t), style);
00365 break;
00366
00367 case IDENTIFIER_NODE:
00368 data_type = IDENTIFIER_POINTER (t);
00369 break;
00370
00371
00372
00373
00374
00375
00376
00377
00378
00379
00380
00381
00382 case RECORD_TYPE:
00383 if (TYPE_NAME (t))
00384 data_type = IDENTIFIER_POINTER (TYPE_NAME (t));
00385 else
00386 {
00387 data_type = "";
00388 chain_p = TYPE_FIELDS (t);
00389 while (chain_p)
00390 {
00391 data_type = concat (data_type, gen_decl (chain_p, 0, ansi),
00392 NULL);
00393 chain_p = TREE_CHAIN (chain_p);
00394 data_type = concat (data_type, "; ", NULL);
00395 }
00396 data_type = concat ("{ ", data_type, "}", NULL);
00397 }
00398 data_type = concat ("struct ", data_type, NULL);
00399 break;
00400
00401 case UNION_TYPE:
00402 if (TYPE_NAME (t))
00403 data_type = IDENTIFIER_POINTER (TYPE_NAME (t));
00404 else
00405 {
00406 data_type = "";
00407 chain_p = TYPE_FIELDS (t);
00408 while (chain_p)
00409 {
00410 data_type = concat (data_type, gen_decl (chain_p, 0, ansi),
00411 NULL);
00412 chain_p = TREE_CHAIN (chain_p);
00413 data_type = concat (data_type, "; ", NULL);
00414 }
00415 data_type = concat ("{ ", data_type, "}", NULL);
00416 }
00417 data_type = concat ("union ", data_type, NULL);
00418 break;
00419
00420 case ENUMERAL_TYPE:
00421 if (TYPE_NAME (t))
00422 data_type = IDENTIFIER_POINTER (TYPE_NAME (t));
00423 else
00424 {
00425 data_type = "";
00426 chain_p = TYPE_VALUES (t);
00427 while (chain_p)
00428 {
00429 data_type = concat (data_type,
00430 IDENTIFIER_POINTER (TREE_PURPOSE (chain_p)), NULL);
00431 chain_p = TREE_CHAIN (chain_p);
00432 if (chain_p)
00433 data_type = concat (data_type, ", ", NULL);
00434 }
00435 data_type = concat ("{ ", data_type, " }", NULL);
00436 }
00437 data_type = concat ("enum ", data_type, NULL);
00438 break;
00439
00440 case TYPE_DECL:
00441 data_type = IDENTIFIER_POINTER (DECL_NAME (t));
00442 break;
00443
00444 case INTEGER_TYPE:
00445 data_type = IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (t)));
00446
00447
00448 if (TREE_UNSIGNED (t) && TYPE_QUALS (t))
00449 data_type = concat ("unsigned ", data_type, NULL);
00450 break;
00451
00452 case REAL_TYPE:
00453 data_type = IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (t)));
00454 break;
00455
00456 case VOID_TYPE:
00457 data_type = "void";
00458 break;
00459
00460 case ERROR_MARK:
00461 data_type = "[ERROR]";
00462 break;
00463
00464 default:
00465 abort ();
00466 }
00467 }
00468 if (TYPE_READONLY (t))
00469 ret_val = concat ("const ", ret_val, NULL);
00470 if (TYPE_VOLATILE (t))
00471 ret_val = concat ("volatile ", ret_val, NULL);
00472 if (TYPE_RESTRICT (t))
00473 ret_val = concat ("restrict ", ret_val, NULL);
00474 return ret_val;
00475 }
00476
00477
00478
00479
00480
00481
00482
00483
00484
00485
00486
00487 static const char *
00488 gen_decl (decl, is_func_definition, style)
00489 tree decl;
00490 int is_func_definition;
00491 formals_style style;
00492 {
00493 const char *ret_val;
00494
00495 if (DECL_NAME (decl))
00496 ret_val = IDENTIFIER_POINTER (DECL_NAME (decl));
00497 else
00498 ret_val = "";
00499
00500
00501
00502
00503
00504 if (style == k_and_r_names)
00505 return ret_val;
00506
00507
00508
00509
00510
00511
00512
00513
00514 if (TREE_THIS_VOLATILE (decl))
00515 ret_val = concat ("volatile ", ret_val, NULL);
00516 if (TREE_READONLY (decl))
00517 ret_val = concat ("const ", ret_val, NULL);
00518
00519 data_type = "";
00520
00521
00522
00523
00524
00525
00526
00527
00528
00529
00530
00531
00532
00533 if (TREE_CODE (decl) == FUNCTION_DECL && is_func_definition)
00534 {
00535 ret_val = concat (ret_val, gen_formal_list_for_func_def (decl, ansi),
00536 NULL);
00537
00538
00539
00540
00541
00542
00543
00544
00545 ret_val = gen_type (ret_val, TREE_TYPE (TREE_TYPE (decl)), style);
00546 }
00547 else
00548 ret_val = gen_type (ret_val, TREE_TYPE (decl), style);
00549
00550 ret_val = affix_data_type (ret_val);
00551
00552 if (TREE_CODE (decl) != FUNCTION_DECL && DECL_REGISTER (decl))
00553 ret_val = concat ("register ", ret_val, NULL);
00554 if (TREE_PUBLIC (decl))
00555 ret_val = concat ("extern ", ret_val, NULL);
00556 if (TREE_CODE (decl) == FUNCTION_DECL && !TREE_PUBLIC (decl))
00557 ret_val = concat ("static ", ret_val, NULL);
00558
00559 return ret_val;
00560 }
00561
00562 extern FILE *aux_info_file;
00563
00564
00565
00566
00567
00568 void
00569 gen_aux_info_record (fndecl, is_definition, is_implicit, is_prototyped)
00570 tree fndecl;
00571 int is_definition;
00572 int is_implicit;
00573 int is_prototyped;
00574 {
00575 if (flag_gen_aux_info)
00576 {
00577 static int compiled_from_record = 0;
00578
00579
00580
00581
00582 if (! compiled_from_record++)
00583 {
00584
00585
00586
00587 fprintf (aux_info_file, "/* compiled from: . */\n");
00588 }
00589
00590
00591
00592 fprintf (aux_info_file, "/* %s:%d:%c%c */ %s;",
00593 DECL_SOURCE_FILE (fndecl),
00594 DECL_SOURCE_LINE (fndecl),
00595 (is_implicit) ? 'I' : (is_prototyped) ? 'N' : 'O',
00596 (is_definition) ? 'F' : 'C',
00597 gen_decl (fndecl, is_definition, ansi));
00598
00599
00600
00601
00602
00603 if (is_definition)
00604 {
00605 fprintf (aux_info_file, " /*%s %s*/",
00606 gen_formal_list_for_func_def (fndecl, k_and_r_names),
00607 gen_formal_list_for_func_def (fndecl, k_and_r_decls));
00608 }
00609
00610 fprintf (aux_info_file, "\n");
00611 }
00612 }