Differences From Artifact [a4202c2dfc]:
- File
src/OFDictionary_hashtable.m
— part of check-in
[f173477bef]
at
2011-09-19 16:34:04
on branch trunk
— Rename -[allocMemoryForNItems:withSize:] and friends.
It is now -[allocMemoryForNItems:ofSize:]. (user: js, size: 17249) [annotate] [blame] [check-ins using]
To Artifact [e193cfb1d7]:
- File
src/OFDictionary_hashtable.m
— part of check-in
[e1e7ffa903]
at
2011-09-22 23:25:42
on branch trunk
— Exceptions are now autoreleased.
This is safe as an "exception loop" can't happen, since if allocating
an exception fails, it throws an OFAllocFailedException which is
preallocated and can always be thrown.So, the worst case would be that an autorelease of an exception fails,
triggering an OFOutOfMemoryException for which there is no memory,
resulting in an OFAllocFailedException to be thrown. (user: js, size: 17408) [annotate] [blame] [check-ins using]
︙ | ︙ | |||
63 64 65 66 67 68 69 | self = [super init]; @try { uint32_t i; OFDictionary_hashtable *hashtable; if (dictionary == nil) | | > | | > | | 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 | self = [super init]; @try { uint32_t i; OFDictionary_hashtable *hashtable; if (dictionary == nil) @throw [OFInvalidArgumentException exceptionWithClass: isa selector: _cmd]; if (![dictionary isKindOfClass: [OFDictionary_hashtable class]] && ![dictionary isKindOfClass: [OFMutableDictionary_hashtable class]]) @throw [OFInvalidArgumentException exceptionWithClass: isa selector: _cmd]; hashtable = (OFDictionary_hashtable*)dictionary; data = [self allocMemoryForNItems: hashtable->size ofSize: sizeof(*data)]; for (i = 0; i < hashtable->size; i++) |
︙ | ︙ | |||
126 127 128 129 130 131 132 | OFEnumerator *enumerator; id key; uint32_t i, newSize; count = [dictionary count]; if (count > UINT32_MAX) | | | | 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 | OFEnumerator *enumerator; id key; uint32_t i, newSize; count = [dictionary count]; if (count > UINT32_MAX) @throw [OFOutOfRangeException exceptionWithClass: isa]; for (newSize = 1; newSize < count; newSize <<= 1); if (newSize == 0) @throw [OFOutOfRangeException exceptionWithClass: isa]; data = [self allocMemoryForNItems: newSize ofSize: sizeof(*data)]; for (i = 0; i < newSize; i++) data[i] = NULL; |
︙ | ︙ | |||
164 165 166 167 168 169 170 | last = hash & (size - 1); for (i = 0; i < last && data[i] != NULL; i++); } if (data[i] != NULL) @throw [OFOutOfRangeException | | | 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 | last = hash & (size - 1); for (i = 0; i < last && data[i] != NULL; i++); } if (data[i] != NULL) @throw [OFOutOfRangeException exceptionWithClass: isa]; bucket = [self allocMemoryWithSize: sizeof(*bucket)]; object = [dictionary objectForKey: key]; bucket->key = [key copy]; bucket->object = [object retain]; |
︙ | ︙ | |||
196 197 198 199 200 201 202 | self = [super init]; @try { uint32_t i; struct of_dictionary_hashtable_bucket *bucket; if (key == nil || object == nil) | | > | | 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 | self = [super init]; @try { uint32_t i; struct of_dictionary_hashtable_bucket *bucket; if (key == nil || object == nil) @throw [OFInvalidArgumentException exceptionWithClass: isa selector: _cmd]; data = [self allocMemoryForNItems: 2 ofSize: sizeof(*data)]; size = 2; for (i = 0; i < size; i++) data[i] = NULL; |
︙ | ︙ | |||
237 238 239 240 241 242 243 | uint32_t i, j, newSize; keysCArray = [keys cArray]; objectsCArray = [objects cArray]; count = [keys count]; if (count > UINT32_MAX) | | | | 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 | uint32_t i, j, newSize; keysCArray = [keys cArray]; objectsCArray = [objects cArray]; count = [keys count]; if (count > UINT32_MAX) @throw [OFOutOfRangeException exceptionWithClass: isa]; for (newSize = 1; newSize < count; newSize <<= 1); if (newSize == 0) @throw [OFOutOfRangeException exceptionWithClass: isa]; data = [self allocMemoryForNItems: newSize ofSize: sizeof(*data)]; for (j = 0; j < newSize; j++) data[j] = NULL; |
︙ | ︙ | |||
294 295 296 297 298 299 300 | for (j = 0; j < last && data[j] != NULL; j++); } if (j >= last) @throw [OFOutOfRangeException | | | 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 | for (j = 0; j < last && data[j] != NULL; j++); } if (j >= last) @throw [OFOutOfRangeException exceptionWithClass: isa]; bucket = [self allocMemoryWithSize: sizeof(*bucket)]; key = [keysCArray[i] copy]; bucket->key = key; bucket->object = [objectsCArray[i] retain]; |
︙ | ︙ | |||
341 342 343 344 345 346 347 | uint32_t i, j, hash, newSize; va_list argumentsCopy; struct of_dictionary_hashtable_bucket *bucket; va_copy(argumentsCopy, arguments); if (firstKey == nil) | | > | | > | | | | 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 | uint32_t i, j, hash, newSize; va_list argumentsCopy; struct of_dictionary_hashtable_bucket *bucket; va_copy(argumentsCopy, arguments); if (firstKey == nil) @throw [OFInvalidArgumentException exceptionWithClass: isa selector: _cmd]; key = firstKey; if ((object = va_arg(arguments, id)) == nil) @throw [OFInvalidArgumentException exceptionWithClass: isa selector: _cmd]; count = 1; for (; va_arg(argumentsCopy, id) != nil; count++); count >>= 1; if (count > UINT32_MAX) @throw [OFOutOfRangeException exceptionWithClass: isa]; for (newSize = 1; newSize < count; newSize <<= 1); if (newSize == 0) @throw [OFOutOfRangeException exceptionWithClass: isa]; data = [self allocMemoryForNItems: newSize ofSize: sizeof(*data)]; for (j = 0; j < newSize; j++) data[j] = NULL; |
︙ | ︙ | |||
389 390 391 392 393 394 395 | uint32_t last; key = va_arg(arguments, id); object = va_arg(arguments, id); if (key == nil || object == nil) @throw [OFInvalidArgumentException | | | | 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 | uint32_t last; key = va_arg(arguments, id); object = va_arg(arguments, id); if (key == nil || object == nil) @throw [OFInvalidArgumentException exceptionWithClass: isa selector: _cmd]; hash = [key hash]; last = size; for (j = hash & (size - 1); j < last && data[j] != NULL; j++) if ([data[j]->key isEqual: key]) |
︙ | ︙ | |||
427 428 429 430 431 432 433 | for (j = 0; j < last && data[j] != NULL; j++); } if (j >= last) @throw [OFOutOfRangeException | | | 432 433 434 435 436 437 438 439 440 441 442 443 444 445 446 | for (j = 0; j < last && data[j] != NULL; j++); } if (j >= last) @throw [OFOutOfRangeException exceptionWithClass: isa]; bucket = [self allocMemoryWithSize: sizeof(*bucket)]; bucket->key = [key copy]; bucket->object = [object retain]; bucket->hash = hash; |
︙ | ︙ | |||
472 473 474 475 476 477 478 | OFArray *keys, *objects; OFEnumerator *keyEnumerator, *objectEnumerator; OFXMLElement *keyElement, *objectElement; if ((![[element name] isEqual: @"OFDictionary"] && ![[element name] isEqual: @"OFMutableDictionary"]) || ![[element namespace] isEqual: OF_SERIALIZATION_NS]) | | > | | > | | 477 478 479 480 481 482 483 484 485 486 487 488 489 490 491 492 493 494 495 496 497 498 499 500 501 502 503 504 505 506 507 508 509 510 511 512 513 514 515 516 517 518 519 520 521 | OFArray *keys, *objects; OFEnumerator *keyEnumerator, *objectEnumerator; OFXMLElement *keyElement, *objectElement; if ((![[element name] isEqual: @"OFDictionary"] && ![[element name] isEqual: @"OFMutableDictionary"]) || ![[element namespace] isEqual: OF_SERIALIZATION_NS]) @throw [OFInvalidArgumentException exceptionWithClass: isa selector: _cmd]; dictionary = [OFMutableDictionary dictionary]; keys = [element elementsForName: @"key" namespace: OF_SERIALIZATION_NS]; objects = [element elementsForName: @"object" namespace: OF_SERIALIZATION_NS]; if ([keys count] != [objects count]) @throw [OFInvalidFormatException exceptionWithClass: isa]; keyEnumerator = [keys objectEnumerator]; objectEnumerator = [objects objectEnumerator]; pool2 = [[OFAutoreleasePool alloc] init]; while ((keyElement = [keyEnumerator nextObject]) != nil && (objectElement = [objectEnumerator nextObject]) != nil) { OFXMLElement *key, *object; key = [[keyElement elementsForNamespace: OF_SERIALIZATION_NS] firstObject]; object = [[objectElement elementsForNamespace: OF_SERIALIZATION_NS] firstObject]; if (key == nil || object == nil) @throw [OFInvalidFormatException exceptionWithClass: isa]; [dictionary setObject: [object objectByDeserializing] forKey: [key objectByDeserializing]]; [pool2 releaseObjects]; } |
︙ | ︙ | |||
524 525 526 527 528 529 530 | } - (id)objectForKey: (id)key { uint32_t i, hash, last; if (key == nil) | | | | 531 532 533 534 535 536 537 538 539 540 541 542 543 544 545 546 | } - (id)objectForKey: (id)key { uint32_t i, hash, last; if (key == nil) @throw [OFInvalidArgumentException exceptionWithClass: isa selector: _cmd]; hash = [key hash]; last = size; for (i = hash & (size - 1); i < last && data[i] != NULL; i++) { if (data[i] == DELETED) continue; |
︙ | ︙ | |||
767 768 769 770 771 772 773 | [super dealloc]; } - (void)reset { if (mutationsPtr != NULL && *mutationsPtr != mutations) @throw [OFEnumerationMutationException | | | | | | | | 774 775 776 777 778 779 780 781 782 783 784 785 786 787 788 789 790 791 792 793 794 795 796 797 798 799 800 801 802 803 804 805 806 807 808 809 810 811 812 813 814 815 816 817 818 819 820 821 822 | [super dealloc]; } - (void)reset { if (mutationsPtr != NULL && *mutationsPtr != mutations) @throw [OFEnumerationMutationException exceptionWithClass: isa object: dictionary]; pos = 0; } @end @implementation OFDictionaryObjectEnumerator_hashtable - (id)nextObject { if (mutationsPtr != NULL && *mutationsPtr != mutations) @throw [OFEnumerationMutationException exceptionWithClass: isa object: dictionary]; for (; pos < size && (data[pos] == NULL || data[pos] == DELETED); pos++); if (pos < size) return data[pos++]->object; else return nil; } @end @implementation OFDictionaryKeyEnumerator_hashtable - (id)nextObject { if (mutationsPtr != NULL && *mutationsPtr != mutations) @throw [OFEnumerationMutationException exceptionWithClass: isa object: dictionary]; for (; pos < size && (data[pos] == NULL || data[pos] == DELETED); pos++); if (pos < size) return data[pos++]->key; else return nil; } @end |