1/* 2 * Copyright (C) 2008 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17/* ---- includes ----------------------------------------------------------- */ 18 19#include "b_BasicEm/Context.h" 20#include "b_BasicEm/MemTbl.h" 21#include "b_BasicEm/Functions.h" 22 23/* ------------------------------------------------------------------------- */ 24 25/* ========================================================================= */ 26/* */ 27/* ---- \ghd{ auxiliary functions } ---------------------------------------- */ 28/* */ 29/* ========================================================================= */ 30 31/* ------------------------------------------------------------------------- */ 32 33flag bbs_MemTbl_memOverlap( const uint16* memPtr1A, uint32 size1A, 34 const uint16* memPtr2A, uint32 size2A ) 35{ 36 int32 diffL = memPtr2A - memPtr1A; 37 if( diffL >= 0 && diffL < ( int32 )size1A ) return TRUE; 38 diffL += ( int32 )size2A; 39 if( diffL >= 0 && diffL < ( int32 )size1A ) return TRUE; 40 return FALSE; 41} 42 43/* ------------------------------------------------------------------------- */ 44 45/* ========================================================================= */ 46/* */ 47/* ---- \ghd{ constructor / destructor } ----------------------------------- */ 48/* */ 49/* ========================================================================= */ 50 51/* ------------------------------------------------------------------------- */ 52 53void bbs_MemTbl_init( struct bbs_Context* cpA, 54 struct bbs_MemTbl* ptrA ) 55{ 56 uint32 iL; 57 for( iL = 0; iL < bbs_MAX_MEM_SEGS; iL++ ) 58 { 59 bbs_MemSeg_init( cpA, &ptrA->esArrE[ iL ] ); 60 bbs_MemSeg_init( cpA, &ptrA->ssArrE[ iL ] ); 61 ptrA->espArrE[ iL ] = NULL; 62 } 63 ptrA->esSizeE = 0; 64 ptrA->ssSizeE = 0; 65} 66 67/* ------------------------------------------------------------------------- */ 68 69void bbs_MemTbl_exit( struct bbs_Context* cpA, 70 struct bbs_MemTbl* ptrA ) 71{ 72 uint32 iL; 73 for( iL = 0; iL < bbs_MAX_MEM_SEGS; iL++ ) 74 { 75 bbs_MemSeg_exit( cpA, &ptrA->esArrE[ iL ] ); 76 bbs_MemSeg_exit( cpA, &ptrA->ssArrE[ iL ] ); 77 ptrA->espArrE[ iL ] = NULL; 78 } 79 ptrA->esSizeE = 0; 80 ptrA->ssSizeE = 0; 81} 82 83/* ------------------------------------------------------------------------- */ 84 85/* ========================================================================= */ 86/* */ 87/* ---- \ghd{ operators } -------------------------------------------------- */ 88/* */ 89/* ========================================================================= */ 90 91/* ------------------------------------------------------------------------- */ 92 93/* ========================================================================= */ 94/* */ 95/* ---- \ghd{ query functions } -------------------------------------------- */ 96/* */ 97/* ========================================================================= */ 98 99/* ------------------------------------------------------------------------- */ 100 101flag bbs_MemTbl_overlap( struct bbs_Context* cpA, 102 struct bbs_MemTbl* ptrA, 103 const void* memPtrA, uint32 sizeA ) 104{ 105 uint32 iL; 106 for( iL = 0; iL < ptrA->esSizeE; iL++ ) 107 { 108 if( bbs_MemTbl_memOverlap( ptrA->espArrE[ iL ]->memPtrE, 109 ptrA->espArrE[ iL ]->sizeE, 110 memPtrA, sizeA ) ) 111 { 112 return TRUE; 113 } 114 } 115 116 for( iL = 0; iL < ptrA->ssSizeE; iL++ ) 117 { 118 if( bbs_MemTbl_memOverlap( ptrA->ssArrE[ iL ].memPtrE, 119 ptrA->ssArrE[ iL ].sizeE, 120 memPtrA, sizeA ) ) 121 { 122 return TRUE; 123 } 124 } 125 126 return FALSE; 127} 128 129/* ------------------------------------------------------------------------- */ 130 131/* ========================================================================= */ 132/* */ 133/* ---- \ghd{ modify functions } ------------------------------------------- */ 134/* */ 135/* ========================================================================= */ 136 137/* ------------------------------------------------------------------------- */ 138 139/* ========================================================================= */ 140/* */ 141/* ---- \ghd{ I/O } -------------------------------------------------------- */ 142/* */ 143/* ========================================================================= */ 144 145/* ------------------------------------------------------------------------- */ 146 147/* ========================================================================= */ 148/* */ 149/* ---- \ghd{ exec functions } --------------------------------------------- */ 150/* */ 151/* ========================================================================= */ 152 153/* ------------------------------------------------------------------------- */ 154 155void bbs_MemTbl_create( struct bbs_Context* cpA, 156 struct bbs_MemTbl* ptrA, 157 void* memPtrA, 158 uint32 sizeA, 159 uint32 sharedSubSizeA ) 160{ 161 if( sharedSubSizeA > sizeA ) 162 { 163 bbs_ERROR0( "struct bbs_MemTbl bbs_MemTbl_create( void* memPtrA, uint32 sizeA, uint32 sharedSubSizeA ):\n" 164 "sharedSubSizeA > sizeA" ); 165 return; 166 } 167 bbs_MemTbl_init( cpA, ptrA ); 168 169 170 ptrA->esArrE[ 0 ] = bbs_MemSeg_create( cpA, memPtrA, sizeA - sharedSubSizeA ); 171 #ifdef HW_TMS320C5x 172 ptrA->ssArrE[ 0 ] = bbs_MemSeg_createShared( cpA, ( uint16* ) ( ( int32 ) ( ( uint16* )memPtrA ) + sizeA - sharedSubSizeA ), sharedSubSizeA ); 173 #else 174 ptrA->ssArrE[ 0 ] = bbs_MemSeg_createShared( cpA, ( uint16* )memPtrA + sizeA - sharedSubSizeA, sharedSubSizeA ); 175 #endif 176 ptrA->espArrE[ 0 ] = &ptrA->esArrE[ 0 ]; 177 178 ptrA->esSizeE = 1; 179 ptrA->ssSizeE = 1; 180} 181 182/* ------------------------------------------------------------------------- */ 183 184void bbs_MemTbl_add( struct bbs_Context* cpA, 185 struct bbs_MemTbl* ptrA, 186 void* memPtrA, 187 uint32 sizeA, 188 uint32 idA ) 189{ 190 if( ptrA->esSizeE == bbs_MAX_MEM_SEGS ) 191 { 192 bbs_ERROR0( "void bbs_MemTbl_add( struct bbs_MemTbl* ptrA, void* memPtrA, uint32 sizeA ):\n" 193 "Table is full! Increase constant bbs_MAX_MEM_SEGS" ); 194 return; 195 } 196 ptrA->esArrE[ ptrA->esSizeE ] = bbs_MemSeg_create( cpA, memPtrA, sizeA ); 197 ptrA->esArrE[ ptrA->esSizeE ].idE = idA; 198 ptrA->espArrE[ ptrA->esSizeE ] = &ptrA->esArrE[ ptrA->esSizeE ]; 199 ptrA->esSizeE++; 200} 201 202/* ------------------------------------------------------------------------- */ 203 204void bbs_MemTbl_addShared( struct bbs_Context* cpA, 205 struct bbs_MemTbl* ptrA, 206 void* memPtrA, 207 uint32 sizeA, 208 uint32 idA ) 209{ 210 if( ptrA->ssSizeE == bbs_MAX_MEM_SEGS ) 211 { 212 bbs_ERROR0( "void bbs_MemTbl_addShared( struct bbs_MemTbl* ptrA, void* memPtrA, uint32 sizeA ):\n" 213 "Table is full! Increase constant bbs_MAX_MEM_SEGS" ); 214 return; 215 } 216 ptrA->ssArrE[ ptrA->ssSizeE ] = bbs_MemSeg_createShared( cpA, memPtrA, sizeA ); 217 ptrA->ssArrE[ ptrA->ssSizeE ].idE = idA; 218 ptrA->ssSizeE++; 219} 220 221/* ------------------------------------------------------------------------- */ 222 223struct bbs_MemSeg* bbs_MemTbl_segPtr( struct bbs_Context* cpA, 224 struct bbs_MemTbl* ptrA, 225 uint32 idA ) 226{ 227 uint32 iL; 228 if( ptrA->esSizeE == 0 ) 229 { 230 bbs_ERROR0( "bbs_MemTbl_segPtr(): Table contains no exclusive segments." ); 231 return NULL; 232 } 233 if( idA > 0 ) 234 { 235 for( iL = 0; iL < ptrA->esSizeE; iL++ ) 236 { 237 if( idA == ptrA->espArrE[ iL ]->idE ) return ptrA->espArrE[ iL ]; 238 } 239 } 240 for( iL = 0; iL < ptrA->esSizeE; iL++ ) 241 { 242 if( ptrA->espArrE[ iL ]->sizeE > 0 || 243 ptrA->espArrE[ iL ]->dynMemManagerPtrE != 0 ) 244 { 245 return ptrA->espArrE[ iL ]; 246 } 247 } 248 bbs_ERR0( bbs_ERR_MEMORY_OVERFLOW, 249 "bbs_MemTbl_segPtr(): Table contains no valid exclusive segments." ); 250 return 0; 251} 252 253/* ------------------------------------------------------------------------- */ 254 255struct bbs_MemSeg* bbs_MemTbl_sharedSegPtr( struct bbs_Context* cpA, 256 struct bbs_MemTbl* ptrA, 257 uint32 idA ) 258{ 259 uint32 iL; 260 if( ptrA->ssSizeE == 0 ) 261 { 262 bbs_ERROR0( "bbs_MemTbl_sharedSegPtr(): Table contains no shared segments." ); 263 return NULL; 264 } 265 if( idA > 0 ) 266 { 267 for( iL = 0; iL < ptrA->ssSizeE; iL++ ) 268 { 269 if( idA == ptrA->ssArrE[ iL ].idE ) return &ptrA->ssArrE[ iL ]; 270 } 271 } 272 for( iL = 0; iL < ptrA->ssSizeE; iL++ ) 273 { 274 if( ptrA->ssArrE[ iL ].sizeE > 0 || 275 ptrA->ssArrE[ iL ].dynMemManagerPtrE != 0 ) 276 { 277 return &ptrA->ssArrE[ iL ]; 278 } 279 } 280 bbs_ERR0( bbs_ERR_MEMORY_OVERFLOW, 281 "bbs_MemTbl_sharedSegPtr(): Table contains no valid shared segments." ); 282 return 0; 283} 284 285/* ------------------------------------------------------------------------- */ 286 287struct bbs_MemSeg* bbs_MemTbl_fastestSegPtr( struct bbs_Context* cpA, 288 struct bbs_MemTbl* ptrA, 289 uint32 minSizeA ) 290{ 291 uint32 iL; 292 for( iL = 0; iL < ptrA->esSizeE; iL++ ) 293 { 294 if( bbs_MemSeg_availableSize( cpA, ptrA->espArrE[ iL ] ) >= minSizeA ) break; 295 } 296 if( iL == ptrA->esSizeE ) 297 { 298 if( ptrA->esSizeE == 0 ) 299 { 300 bbs_ERROR0( "struct bbs_MemSeg* bbs_MemTbl_fastestSegPtr( struct bbs_MemTbl* ptrA, uint32 minSizeA ):\n" 301 "Table contains no exclusive segments" ); 302 return NULL; 303 } 304 else 305 { 306 bbs_ERR0( bbs_ERR_MEMORY_OVERFLOW, 307 "struct bbs_MemSeg* bbs_MemTbl_fastestSegPtr( struct bbs_MemTbl* ptrA, uint32 minSizeA ):\n" 308 "Could not find segment with sufficient free space" ); 309 return NULL; 310 } 311 } 312 if( ptrA->espArrE[ iL ]->sharedE ) 313 { 314 bbs_ERROR0( "struct bbs_MemSeg* bbs_MemTbl_fastestSegPtr( struct bbs_MemTbl* ptrA, uint32 minSizeA ):\n" 315 "Table corrupt: Found shared segment in exclusive table" ); 316 return NULL; 317 } 318 319 return ptrA->espArrE[ iL ]; 320} 321 322/* ------------------------------------------------------------------------- */ 323 324struct bbs_MemSeg* bbs_MemTbl_largestSegPtr( struct bbs_Context* cpA, 325 struct bbs_MemTbl* ptrA ) 326{ 327 uint32 iL; 328 uint32 maxIndexL = 0; 329 uint32 maxSizeL = 0; 330 331 if( ptrA->esSizeE == 0 ) 332 { 333 bbs_ERROR0( "struct bbs_MemSeg* bbs_MemTbl_largestSegPtr( struct bbs_MemTbl* ptrA ):\n" 334 "No exclusive segments available" ); 335 return NULL; 336 } 337 338 for( iL = 0; iL < ptrA->esSizeE; iL++ ) 339 { 340 uint32 sizeL = bbs_MemSeg_availableSize( cpA, ptrA->espArrE[ iL ] ); 341 if( sizeL > maxSizeL ) 342 { 343 maxSizeL = sizeL; 344 maxIndexL = iL; 345 } 346 } 347 348 if( ptrA->espArrE[ maxIndexL ]->sharedE ) 349 { 350 bbs_ERROR0( "struct bbs_MemSeg* bbs_MemTbl_largestSegPtr( struct bbs_MemTbl* ptrA ):\n" 351 "Table corrupt: Found shared segment in exclusive table" ); 352 return NULL; 353 } 354 355 return ptrA->espArrE[ maxIndexL ]; 356} 357 358/* ------------------------------------------------------------------------- */ 359 360struct bbs_MemSeg* bbs_MemTbl_fastestSharedSegPtr( struct bbs_Context* cpA, 361 struct bbs_MemTbl* ptrA, 362 uint32 minSizeA ) 363{ 364 uint32 iL; 365 for( iL = 0; iL < ptrA->ssSizeE; iL++ ) 366 { 367 if( bbs_MemSeg_availableSize( cpA, &ptrA->ssArrE[ iL ] ) >= minSizeA ) break; 368 } 369 if( iL == ptrA->ssSizeE ) 370 { 371 if( ptrA->esSizeE == 0 ) 372 { 373 bbs_ERROR0( "struct bbs_MemSeg* bbs_MemTbl_fastestSegPtr( struct bbs_MemTbl* ptrA, uint32 minSizeA ):\n" 374 "Table contains no shared segments" ); 375 return NULL; 376 } 377 else 378 { 379 bbs_ERR0( bbs_ERR_MEMORY_OVERFLOW, 380 "struct bbs_MemSeg* bbs_MemTbl_fastestSharedSegPtr( struct bbs_MemTbl* ptrA, uint32 minSizeA ):\n" 381 "Could not find segment with sufficient free space" ); 382 return NULL; 383 } 384 } 385 if( !ptrA->ssArrE[ iL ].sharedE ) 386 { 387 bbs_ERROR0( "struct bbs_MemSeg* bbs_MemTbl_fastestSharedSegPtr( struct bbs_MemTbl* ptrA, uint32 minSizeA ):\n" 388 "Table corrupt: Found exclusive segment in shared table" ); 389 return NULL; 390 } 391 392 return &ptrA->ssArrE[ iL ]; 393} 394 395/* ------------------------------------------------------------------------- */ 396 397struct bbs_MemSeg* bbs_MemTbl_largestSharedSegPtr( struct bbs_Context* cpA, 398 struct bbs_MemTbl* ptrA ) 399{ 400 uint32 iL; 401 uint32 maxIndexL = 0; 402 uint32 maxSizeL = 0; 403 404 if( ptrA->ssSizeE == 0 ) 405 { 406 bbs_ERROR0( "struct bbs_MemSeg* bbs_MemTbl_largestSharedSegPtr( struct bbs_MemTbl* ptrA ):\n" 407 "No shared segments available" ); 408 return NULL; 409 } 410 411 for( iL = 0; iL < ptrA->ssSizeE; iL++ ) 412 { 413 uint32 sizeL = bbs_MemSeg_availableSize( cpA, &ptrA->ssArrE[ iL ] ); 414 if( sizeL > maxSizeL ) 415 { 416 maxSizeL = sizeL; 417 maxIndexL = iL; 418 } 419 } 420 421 if( !ptrA->ssArrE[ maxIndexL ].sharedE ) 422 { 423 bbs_ERROR0( "struct bbs_MemSeg* bbs_MemTbl_largestSharedSegPtr( struct bbs_MemTbl* ptrA ):\n" 424 "Table corrupt: Found exclusive segment in shared table" ); 425 return NULL; 426 } 427 428 return &ptrA->ssArrE[ maxIndexL ]; 429} 430 431/* ------------------------------------------------------------------------- */ 432 433/* ========================================================================= */ 434 435 436