1 2 /**-------------------------------------------------------------------** 3 ** CLooG ** 4 **-------------------------------------------------------------------** 5 ** block.c ** 6 **-------------------------------------------------------------------** 7 ** First version: june 11th 2005 ** 8 **-------------------------------------------------------------------**/ 9 10 11/****************************************************************************** 12 * CLooG : the Chunky Loop Generator (experimental) * 13 ****************************************************************************** 14 * * 15 * Copyright (C) 2001-2005 Cedric Bastoul * 16 * * 17 * This library is free software; you can redistribute it and/or * 18 * modify it under the terms of the GNU Lesser General Public * 19 * License as published by the Free Software Foundation; either * 20 * version 2.1 of the License, or (at your option) any later version. * 21 * * 22 * This library is distributed in the hope that it will be useful, * 23 * but WITHOUT ANY WARRANTY; without even the implied warranty of * 24 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * 25 * Lesser General Public License for more details. * 26 * * 27 * You should have received a copy of the GNU Lesser General Public * 28 * License along with this library; if not, write to the Free Software * 29 * Foundation, Inc., 51 Franklin Street, Fifth Floor, * 30 * Boston, MA 02110-1301 USA * 31 * * 32 * CLooG, the Chunky Loop Generator * 33 * Written by Cedric Bastoul, Cedric.Bastoul@inria.fr * 34 * * 35 ******************************************************************************/ 36/* CAUTION: the english used for comments is probably the worst you ever read, 37 * please feel free to correct and improve it ! 38 */ 39 40# include <stdlib.h> 41# include <stdio.h> 42# include "../include/cloog/cloog.h" 43 44 45/****************************************************************************** 46 * Memory leaks hunting * 47 ******************************************************************************/ 48 49 50/** 51 * These functions and global variables are devoted to memory leaks hunting: we 52 * want to know at each moment how many CloogBlock structures had been allocated 53 * (cloog_block_allocated) and how many had been freed (cloog_block_freed). 54 * Each time a CloogBlock structure is allocated, a call to the function 55 * cloog_block_leak_up() must be carried out, and respectively 56 * cloog_block_leak_down() when a CloogBlock structure is freed. The special 57 * variable cloog_block_max gives the maximal number of CloogBlock structures 58 * simultaneously alive (i.e. allocated and non-freed) in memory. 59 * - June 11th 2005: first version. 60 */ 61 62 63static void cloog_block_leak_up(CloogState *state) 64{ 65 state->block_allocated++; 66 if ((state->block_allocated - state->block_freed) > state->block_max) 67 state->block_max = state->block_allocated - state->block_freed; 68} 69 70 71static void cloog_block_leak_down(CloogState *state) 72{ 73 state->block_freed++; 74} 75 76 77/****************************************************************************** 78 * Structure display function * 79 ******************************************************************************/ 80 81 82/** 83 * cloog_domain_print_structure : 84 * this function is a human-friendly way to display the CloogDomain data 85 * structure, it includes an indentation level (level) in order to work with 86 * others print_structure functions. 87 * - June 16th 2005: first version. 88 */ 89void cloog_block_print_structure(FILE * file, CloogBlock * block, int level) 90{ int i ; 91 92 /* Go to the right level. */ 93 for (i=0; i<level; i++) 94 fprintf(file,"|\t") ; 95 96 if (block != NULL) 97 { fprintf(file,"+-- CloogBlock\n") ; 98 99 /* A blank line. */ 100 for (i=0; i<level+2; i++) 101 fprintf(file,"|\t") ; 102 fprintf(file,"\n") ; 103 104 /* Print statement list. */ 105 cloog_statement_print_structure(file,block->statement,level+1) ; 106 107 /* A blank line. */ 108 for (i=0; i<level+2; i++) 109 fprintf(file,"|\t") ; 110 fprintf(file,"\n") ; 111 112 /* Print scattering function. */ 113 for(i=0; i<level+1; i++) 114 fprintf(file,"|\t") ; 115 116 fprintf(file,"+-- Null scattering function\n") ; 117 118 /* A blank line. */ 119 for (i=0; i<level+2; i++) 120 fprintf(file,"|\t") ; 121 fprintf(file,"\n") ; 122 123 /* Print scalar dimensions. */ 124 for (i=0; i<level+1; i++) 125 fprintf(file,"|\t") ; 126 127 if (block->nb_scaldims == 0) 128 fprintf(file,"No scalar dimensions\n") ; 129 else 130 { fprintf(file,"Scalar dimensions (%d):",block->nb_scaldims) ; 131 for (i = 0; i < block->nb_scaldims; i++) { 132 fprintf(file, " "); 133 cloog_int_print(file, block->scaldims[i]); 134 } 135 fprintf(file,"\n") ; 136 } 137 138 /* A blank line. */ 139 for (i=0; i<level+2; i++) 140 fprintf(file,"|\t") ; 141 fprintf(file,"\n") ; 142 143 /* Print depth. */ 144 for (i=0; i<level+1; i++) 145 fprintf(file,"|\t") ; 146 fprintf(file,"Depth: %d\n",block->depth) ; 147 148 /* A blank line. */ 149 for (i=0; i<level+1; i++) 150 fprintf(file,"|\t") ; 151 fprintf(file,"\n") ; 152 } 153 else 154 fprintf(file,"+-- Null CloogBlock\n") ; 155} 156 157 158/** 159 * cloog_block_print function: 160 * This function prints the content of a CloogBlock structure (block) into a 161 * file (file, possibly stdout). 162 * - June 11th 2005: first version. 163 * - June 16th 2005: now just a call to cloog_block_print_structure. 164 */ 165void cloog_block_print(FILE * file, CloogBlock * block) 166{ cloog_block_print_structure(file,block,0) ; 167} 168 169 170/** 171 * cloog_block_list_print function: 172 * This function prints the content of a CloogBlock structure (block) into a 173 * file (file, possibly stdout). 174 * - June 16th 2005: first version. 175 */ 176void cloog_block_list_print(FILE * file, CloogBlockList * blocklist) 177{ int i=0 ; 178 179 while (blocklist != NULL) 180 { fprintf(file,"+-- CloogBlockList node %d\n",i) ; 181 cloog_block_print_structure(file,blocklist->block,1) ; 182 blocklist = blocklist->next ; 183 i++ ; 184 } 185} 186 187 188/****************************************************************************** 189 * Memory deallocation function * 190 ******************************************************************************/ 191 192 193/** 194 * cloog_block_free function: 195 * This function frees the allocated memory for a CloogStatement structure. 196 * - June 11th 2005: first version. 197 * - June 30th 2005: scaldims field management. 198 */ 199void cloog_block_free(CloogBlock * block) 200{ int i ; 201 202 if (block != NULL) 203 { block->references -- ; 204 205 if (block->references == 0) { 206 cloog_block_leak_down(block->state); 207 if (block->scaldims != NULL) 208 { for (i=0;i<block->nb_scaldims;i++) 209 cloog_int_clear(block->scaldims[i]); 210 211 free(block->scaldims) ; 212 } 213 if (block->statement) 214 cloog_statement_free(block->statement); 215 free(block) ; 216 } 217 } 218} 219 220 221/** 222 * cloog_block_list_free function: 223 * This function frees the allocated memory for a CloogBlockList structure. 224 * - June 11th 2005: first version. 225 */ 226void cloog_block_list_free(CloogBlockList * blocklist) 227{ CloogBlockList * temp ; 228 229 while (blocklist != NULL) 230 { temp = blocklist->next ; 231 cloog_block_free(blocklist->block) ; 232 free(blocklist) ; 233 blocklist = temp ; 234 } 235} 236 237 238/****************************************************************************** 239 * Processing functions * 240 ******************************************************************************/ 241 242/** 243 * cloog_block_malloc function: 244 * This function allocates the memory space for a CloogBlock structure and 245 * sets its fields with default values. Then it returns a pointer to the 246 * allocated space. 247 * - November 21th 2005: first version. 248 */ 249CloogBlock *cloog_block_malloc(CloogState *state) 250{ CloogBlock * block ; 251 252 /* Memory allocation for the CloogBlock structure. */ 253 block = (CloogBlock *)malloc(sizeof(CloogBlock)) ; 254 if (block == NULL) 255 cloog_die("memory overflow.\n"); 256 cloog_block_leak_up(state); 257 258 /* We set the various fields with default values. */ 259 block->state = state; 260 block->statement = NULL ; 261 block->nb_scaldims = 0 ; 262 block->scaldims = NULL ; 263 block->depth = 0 ; 264 block->references = 1 ; 265 block->usr = NULL; 266 267 return block ; 268} 269 270 271/** 272 * cloog_block_alloc function: 273 * This function allocates the memory space for a CloogBlock structure and 274 * sets its fields with those given as input. Then it returns a pointer to the 275 * allocated space. The two parameters nb_scaldims and scaldims are for internal 276 * service, put to respectively 0 and NULL if you don't know what they are 277 * useful for ! 278 * - statement is the statement list of the block, 279 * - scattering is the scattering function for the block (NULL if unsure !), 280 * - nb_scaldims is the number of scalar dimensions (0 if unsure !), 281 * - scaldims is the array with the scalar dimensions values (NULL if unsure !), 282 * - depth is the original block depth (the number of outer loops). 283 ** 284 * - June 11th 2005: first version. 285 * - June 30th 2005: addition of the nb_scaldims and scaldims parameters. 286 * - November 21th 2005: use of cloog_block_malloc. 287 */ 288CloogBlock *cloog_block_alloc(CloogStatement *statement, int nb_scaldims, 289 cloog_int_t *scaldims, int depth) 290{ CloogBlock * block ; 291 292 /* Block allocation. */ 293 block = cloog_block_malloc(statement->state); 294 295 block->statement = statement ; 296 block->nb_scaldims = nb_scaldims ; 297 block->scaldims = scaldims ; 298 block->depth = depth ; 299 block->references = 1 ; 300 301 return block ; 302} 303 304 305/** 306 * cloog_block_list_malloc function: 307 * This function allocates the memory space for a CloogBlockList structure and 308 * sets its fields with default values. Then it returns a pointer to the 309 * allocated space. 310 * - November 21th 2005: first version. 311 */ 312CloogBlockList * cloog_block_list_malloc() 313{ CloogBlockList * blocklist ; 314 315 /* Memory allocation for the CloogBlock structure. */ 316 blocklist = (CloogBlockList *)malloc(sizeof(CloogBlockList)) ; 317 if (blocklist == NULL) 318 cloog_die("memory overflow.\n"); 319 320 /* We set the various fields with default values. */ 321 blocklist->block = NULL ; 322 blocklist->next = NULL ; 323 324 return blocklist ; 325} 326 327 328/** 329 * cloog_block_list_alloc function: 330 * This function allocates the memory space for a CloogBlockList structure and 331 * sets its fields with those given as input. Then it returns a pointer to the 332 * allocated space. 333 * - block is the block element of the list node, 334 ** 335 * - June 11th 2005: first version. 336 * - November 21th 2005: use of cloog_block_list_malloc. 337 */ 338CloogBlockList * cloog_block_list_alloc(CloogBlock * block) 339{ CloogBlockList * blocklist ; 340 341 /* Block list node allocation. */ 342 blocklist = cloog_block_list_malloc() ; 343 344 blocklist->block = block ; 345 blocklist->block->references ++ ; /* The block has a new reference to it. */ 346 blocklist->next = NULL ; 347 348 return blocklist ; 349} 350 351 352/** 353 * cloog_block_copy function: 354 * This function returns a copy of a CloogBlock structure 'block'. To save 355 * memory this is not a memory copy but we increment a counter of active 356 * references inside the structure, then return a pointer to that structure. 357 */ 358CloogBlock * cloog_block_copy(CloogBlock * block) 359{ if (block == NULL) 360 return NULL ; 361 362 block->references ++ ; 363 return block ; 364} 365 366 367/** 368 * cloog_block_merge function: 369 * this function adds at the end of the statement list of the block 'block', 370 * the statement list of the block 'merged'. Then the CloogBlock structure 371 * of 'merged' is freed (obviously not its statement list that is now 372 * included in 'block'). 373 * - June 11th 2005: first version. 374 */ 375void cloog_block_merge(CloogBlock * block, CloogBlock * merged) 376{ CloogStatement * statement ; 377 378 if ((block == NULL) || (merged == NULL)) 379 return ; 380 381 if (block->statement != NULL) 382 { statement = block->statement ; 383 384 while (statement->next != NULL) 385 statement = statement->next ; 386 387 statement->next = merged->statement ; 388 } 389 else 390 block->statement = merged->statement ; 391 392 merged->statement = NULL; 393 cloog_block_free(merged); 394} 395 396 397 398 399 400 401 402 403 404 405