schedule.c 4.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165
  1. /*
  2. * Copyright 2010-2011 INRIA Saclay
  3. *
  4. * Use of this software is governed by the MIT license
  5. *
  6. * Written by Sven Verdoolaege, INRIA Saclay - Ile-de-France,
  7. * Parc Club Orsay Universite, ZAC des vignes, 4 rue Jacques Monod,
  8. * 91893 Orsay, France
  9. */
  10. #include <assert.h>
  11. #include <ctype.h>
  12. #include <stdio.h>
  13. #include <string.h>
  14. #include <isl/set.h>
  15. #include <isl/map.h>
  16. #include <isl/constraint.h>
  17. #include "schedule.h"
  18. /* Add parameters with identifiers "ids" to "set".
  19. */
  20. static __isl_give isl_set *add_params(__isl_take isl_set *set,
  21. __isl_keep isl_id_list *ids)
  22. {
  23. int i, n;
  24. unsigned nparam;
  25. n = isl_id_list_n_id(ids);
  26. nparam = isl_set_dim(set, isl_dim_param);
  27. set = isl_set_add_dims(set, isl_dim_param, n);
  28. for (i = 0; i < n; ++i) {
  29. isl_id *id;
  30. id = isl_id_list_get_id(ids, i);
  31. set = isl_set_set_dim_id(set, isl_dim_param, nparam + i, id);
  32. }
  33. return set;
  34. }
  35. /* Equate the dimensions of "set" starting at "first" to
  36. * freshly created parameters with identifiers "ids".
  37. * The number of equated dimensions is equal to the number of elements in "ids".
  38. */
  39. static __isl_give isl_set *parametrize(__isl_take isl_set *set,
  40. int first, __isl_keep isl_id_list *ids)
  41. {
  42. int i, n;
  43. unsigned nparam;
  44. nparam = isl_set_dim(set, isl_dim_param);
  45. set = add_params(set, ids);
  46. n = isl_id_list_n_id(ids);
  47. for (i = 0; i < n; ++i)
  48. set = isl_set_equate(set, isl_dim_param, nparam + i,
  49. isl_dim_set, first + i);
  50. return set;
  51. }
  52. /* Given a parameter space "space", create a set of dimension "len"
  53. * of which the dimensions starting at "first" are equated to
  54. * freshly created parameters with identifiers "ids".
  55. */
  56. __isl_give isl_set *parametrization(__isl_take isl_space *space,
  57. int len, int first, __isl_keep isl_id_list *ids)
  58. {
  59. isl_set *set;
  60. space = isl_space_set_from_params(space);
  61. space = isl_space_add_dims(space, isl_dim_set, len);
  62. set = isl_set_universe(space);
  63. return parametrize(set, first, ids);
  64. }
  65. /* Load and return a schedule from a file called "filename".
  66. */
  67. static __isl_give isl_schedule *load_schedule(isl_ctx *ctx,
  68. const char *filename)
  69. {
  70. FILE *file;
  71. isl_schedule *schedule;
  72. file = fopen(filename, "r");
  73. if (!file) {
  74. fprintf(stderr, "Unable to open '%s' for reading\n", filename);
  75. return NULL;
  76. }
  77. schedule = isl_schedule_read_from_file(ctx, file);
  78. fclose(file);
  79. return schedule;
  80. }
  81. /* Save the schedule "schedule" to a file called "filename".
  82. * The schedule is printed in block style.
  83. */
  84. static void save_schedule(__isl_keep isl_schedule *schedule,
  85. const char *filename)
  86. {
  87. FILE *file;
  88. isl_ctx *ctx;
  89. isl_printer *p;
  90. if (!schedule)
  91. return;
  92. file = fopen(filename, "w");
  93. if (!file) {
  94. fprintf(stderr, "Unable to open '%s' for writing\n", filename);
  95. return;
  96. }
  97. ctx = isl_schedule_get_ctx(schedule);
  98. p = isl_printer_to_file(ctx, file);
  99. p = isl_printer_set_yaml_style(p, ISL_YAML_STYLE_BLOCK);
  100. p = isl_printer_print_schedule(p, schedule);
  101. isl_printer_free(p);
  102. fclose(file);
  103. }
  104. /* Obtain a schedule, either by reading it form a file
  105. * or by computing it using "compute".
  106. * Also take care of saving the computed schedule and/or
  107. * dumping the obtained schedule if requested by the user.
  108. */
  109. __isl_give isl_schedule *ppcg_get_schedule(isl_ctx *ctx,
  110. struct ppcg_options *options,
  111. __isl_give isl_schedule *(*compute)(void *user), void *user)
  112. {
  113. isl_schedule *schedule;
  114. if (options->load_schedule_file) {
  115. schedule = load_schedule(ctx, options->load_schedule_file);
  116. } else {
  117. schedule = compute(user);
  118. if (options->save_schedule_file)
  119. save_schedule(schedule, options->save_schedule_file);
  120. }
  121. if (options->debug->dump_schedule)
  122. isl_schedule_dump(schedule);
  123. return schedule;
  124. }
  125. /* Mark all dimensions in the band node "node" to be of "type".
  126. */
  127. __isl_give isl_schedule_node *ppcg_set_schedule_node_type(
  128. __isl_take isl_schedule_node *node, enum isl_ast_loop_type type)
  129. {
  130. int i, n;
  131. n = isl_schedule_node_band_n_member(node);
  132. for (i = 0; i < n; ++i)
  133. node = isl_schedule_node_band_member_set_ast_loop_type(node, i,
  134. type);
  135. return node;
  136. }