Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(3)

Side by Side Diff: Source/WebCore/rendering/RenderCounter.cpp

Issue 8206006: Merge 96632 - Source/WebCore: Hold refptr to identified previous sibling within findPlaceForCounter. (Closed) Base URL: http://svn.webkit.org/repository/webkit/branches/chromium/874/
Patch Set: Created 9 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « LayoutTests/fast/css/counters/counter-after-style-crash-expected.txt ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /** 1 /**
2 * Copyright (C) 2004 Allan Sandfeld Jensen (kde@carewolf.com) 2 * Copyright (C) 2004 Allan Sandfeld Jensen (kde@carewolf.com)
3 * Copyright (C) 2006, 2007 Apple Inc. All rights reserved. 3 * Copyright (C) 2006, 2007 Apple Inc. All rights reserved.
4 * 4 *
5 * This library is free software; you can redistribute it and/or 5 * This library is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU Library General Public 6 * modify it under the terms of the GNU Library General Public
7 * License as published by the Free Software Foundation; either 7 * License as published by the Free Software Foundation; either
8 * version 2 of the License, or (at your option) any later version. 8 * version 2 of the License, or (at your option) any later version.
9 * 9 *
10 * This library is distributed in the hope that it will be useful, 10 * This library is distributed in the hope that it will be useful,
(...skipping 285 matching lines...) Expand 10 before | Expand all | Expand 10 after
296 static bool findPlaceForCounter(RenderObject* counterOwner, const AtomicString& identifier, bool isReset, CounterNode*& parent, CounterNode*& previousSibling) 296 static bool findPlaceForCounter(RenderObject* counterOwner, const AtomicString& identifier, bool isReset, CounterNode*& parent, CounterNode*& previousSibling)
297 { 297 {
298 // We cannot stop searching for counters with the same identifier before we also 298 // We cannot stop searching for counters with the same identifier before we also
299 // check this renderer, because it may affect the positioning in the tree of our counter. 299 // check this renderer, because it may affect the positioning in the tree of our counter.
300 RenderObject* searchEndRenderer = previousSiblingOrParent(counterOwner); 300 RenderObject* searchEndRenderer = previousSiblingOrParent(counterOwner);
301 // We check renderers in preOrder from the renderer that our counter is atta ched to 301 // We check renderers in preOrder from the renderer that our counter is atta ched to
302 // towards the begining of the document for counters with the same identifie r as the one 302 // towards the begining of the document for counters with the same identifie r as the one
303 // we are trying to find a place for. This is the next renderer to be checke d. 303 // we are trying to find a place for. This is the next renderer to be checke d.
304 RenderObject* currentRenderer = previousInPreOrder(counterOwner); 304 RenderObject* currentRenderer = previousInPreOrder(counterOwner);
305 previousSibling = 0; 305 previousSibling = 0;
306 RefPtr<CounterNode> previousSiblingProtector = 0;
307
306 while (currentRenderer) { 308 while (currentRenderer) {
307 CounterNode* currentCounter = makeCounterNode(currentRenderer, identifie r, false); 309 CounterNode* currentCounter = makeCounterNode(currentRenderer, identifie r, false);
308 if (searchEndRenderer == currentRenderer) { 310 if (searchEndRenderer == currentRenderer) {
309 // We may be at the end of our search. 311 // We may be at the end of our search.
310 if (currentCounter) { 312 if (currentCounter) {
311 // We have a suitable counter on the EndSearchRenderer. 313 // We have a suitable counter on the EndSearchRenderer.
312 if (previousSibling) { // But we already found another counter t hat we come after. 314 if (previousSiblingProtector) { // But we already found another counter that we come after.
313 if (currentCounter->actsAsReset()) { 315 if (currentCounter->actsAsReset()) {
314 // We found a reset counter that is on a renderer that i s a sibling of ours or a parent. 316 // We found a reset counter that is on a renderer that i s a sibling of ours or a parent.
315 if (isReset && areRenderersElementsSiblings(currentRende rer, counterOwner)) { 317 if (isReset && areRenderersElementsSiblings(currentRende rer, counterOwner)) {
316 // We are also a reset counter and the previous rese t was on a sibling renderer 318 // We are also a reset counter and the previous rese t was on a sibling renderer
317 // hence we are the next sibling of that counter if that reset is not a root or 319 // hence we are the next sibling of that counter if that reset is not a root or
318 // we are a root node if that reset is a root. 320 // we are a root node if that reset is a root.
319 parent = currentCounter->parent(); 321 parent = currentCounter->parent();
320 previousSibling = parent ? currentCounter : 0; 322 previousSibling = parent ? currentCounter : 0;
321 return parent; 323 return parent;
322 } 324 }
323 // We are not a reset node or the previous reset must be on an ancestor of our owner renderer 325 // We are not a reset node or the previous reset must be on an ancestor of our owner renderer
324 // hence we must be a child of that reset counter. 326 // hence we must be a child of that reset counter.
325 parent = currentCounter; 327 parent = currentCounter;
326 // In some cases renders can be reparented (ex. nodes in side a table but not in a column or row). 328 // In some cases renders can be reparented (ex. nodes in side a table but not in a column or row).
327 // In these cases the identified previousSibling will be invalid as its parent is different from 329 // In these cases the identified previousSibling will be invalid as its parent is different from
328 // our identified parent. 330 // our identified parent.
329 if (previousSibling->parent() != currentCounter) 331 if (previousSiblingProtector->parent() != currentCounter )
330 previousSibling = 0; 332 previousSiblingProtector = 0;
333
334 previousSibling = previousSiblingProtector.get();
331 return true; 335 return true;
332 } 336 }
333 // CurrentCounter, the counter at the EndSearchRenderer, is not reset. 337 // CurrentCounter, the counter at the EndSearchRenderer, is not reset.
334 if (!isReset || !areRenderersElementsSiblings(currentRendere r, counterOwner)) { 338 if (!isReset || !areRenderersElementsSiblings(currentRendere r, counterOwner)) {
335 // If the node we are placing is not reset or we have fo und a counter that is attached 339 // If the node we are placing is not reset or we have fo und a counter that is attached
336 // to an ancestor of the placed counter's owner renderer we know we are a sibling of that node. 340 // to an ancestor of the placed counter's owner renderer we know we are a sibling of that node.
337 ASSERT(currentCounter->parent() == previousSibling->pare nt()); 341 ASSERT(currentCounter->parent() == previousSiblingProtec tor->parent());
338 parent = currentCounter->parent(); 342 parent = currentCounter->parent();
343 previousSibling = previousSiblingProtector.get();
339 return true; 344 return true;
340 } 345 }
341 } else { 346 } else {
342 // We are at the potential end of the search, but we had no previous sibling candidate 347 // We are at the potential end of the search, but we had no previous sibling candidate
343 // In this case we follow pretty much the same logic as abov e but no ASSERTs about 348 // In this case we follow pretty much the same logic as abov e but no ASSERTs about
344 // previousSibling, and when we are a sibling of the end cou nter we must set previousSibling 349 // previousSibling, and when we are a sibling of the end cou nter we must set previousSibling
345 // to currentCounter. 350 // to currentCounter.
346 if (currentCounter->actsAsReset()) { 351 if (currentCounter->actsAsReset()) {
347 if (isReset && areRenderersElementsSiblings(currentRende rer, counterOwner)) { 352 if (isReset && areRenderersElementsSiblings(currentRende rer, counterOwner)) {
348 parent = currentCounter->parent(); 353 parent = currentCounter->parent();
349 previousSibling = currentCounter; 354 previousSibling = currentCounter;
350 return parent; 355 return parent;
351 } 356 }
352 parent = currentCounter; 357 parent = currentCounter;
358 previousSibling = previousSiblingProtector.get();
353 return true; 359 return true;
354 } 360 }
355 if (!isReset || !areRenderersElementsSiblings(currentRendere r, counterOwner)) { 361 if (!isReset || !areRenderersElementsSiblings(currentRendere r, counterOwner)) {
356 parent = currentCounter->parent(); 362 parent = currentCounter->parent();
357 previousSibling = currentCounter; 363 previousSibling = currentCounter;
358 return true; 364 return true;
359 } 365 }
360 previousSibling = currentCounter; 366 previousSiblingProtector = currentCounter;
361 } 367 }
362 } 368 }
363 // We come here if the previous sibling or parent of our owner rende rer had no 369 // We come here if the previous sibling or parent of our owner rende rer had no
364 // good counter, or we are a reset node and the counter on the previ ous sibling 370 // good counter, or we are a reset node and the counter on the previ ous sibling
365 // of our owner renderer was not a reset counter. 371 // of our owner renderer was not a reset counter.
366 // Set a new goal for the end of the search. 372 // Set a new goal for the end of the search.
367 searchEndRenderer = previousSiblingOrParent(currentRenderer); 373 searchEndRenderer = previousSiblingOrParent(currentRenderer);
368 } else { 374 } else {
369 // We are searching descendants of a previous sibling of the rendere r that the 375 // We are searching descendants of a previous sibling of the rendere r that the
370 // counter being placed is attached to. 376 // counter being placed is attached to.
371 if (currentCounter) { 377 if (currentCounter) {
372 // We found a suitable counter. 378 // We found a suitable counter.
373 if (previousSibling) { 379 if (previousSiblingProtector) {
374 // Since we had a suitable previous counter before, we shoul d only consider this one as our 380 // Since we had a suitable previous counter before, we shoul d only consider this one as our
375 // previousSibling if it is a reset counter and hence the cu rrent previousSibling is its child. 381 // previousSibling if it is a reset counter and hence the cu rrent previousSibling is its child.
376 if (currentCounter->actsAsReset()) { 382 if (currentCounter->actsAsReset()) {
377 previousSibling = currentCounter; 383 previousSiblingProtector = currentCounter;
378 // We are no longer interested in previous siblings of t he currentRenderer or their children 384 // We are no longer interested in previous siblings of t he currentRenderer or their children
379 // as counters they may have attached cannot be the prev ious sibling of the counter we are placing. 385 // as counters they may have attached cannot be the prev ious sibling of the counter we are placing.
380 currentRenderer = parentElement(currentRenderer)->render er(); 386 currentRenderer = parentElement(currentRenderer)->render er();
381 continue; 387 continue;
382 } 388 }
383 } else 389 } else
384 previousSibling = currentCounter; 390 previousSiblingProtector = currentCounter;
385 currentRenderer = previousSiblingOrParent(currentRenderer); 391 currentRenderer = previousSiblingOrParent(currentRenderer);
386 continue; 392 continue;
387 } 393 }
388 } 394 }
389 // This function is designed so that the same test is not done twice in an iteration, except for this one 395 // This function is designed so that the same test is not done twice in an iteration, except for this one
390 // which may be done twice in some cases. Rearranging the decision point s though, to accommodate this 396 // which may be done twice in some cases. Rearranging the decision point s though, to accommodate this
391 // performance improvement would create more code duplication than is wo rthwhile in my oppinion and may further 397 // performance improvement would create more code duplication than is wo rthwhile in my oppinion and may further
392 // impede the readability of this already complex algorithm. 398 // impede the readability of this already complex algorithm.
393 if (previousSibling) 399 if (previousSiblingProtector)
394 currentRenderer = previousSiblingOrParent(currentRenderer); 400 currentRenderer = previousSiblingOrParent(currentRenderer);
395 else 401 else
396 currentRenderer = previousInPreOrder(currentRenderer); 402 currentRenderer = previousInPreOrder(currentRenderer);
397 } 403 }
398 return false; 404 return false;
399 } 405 }
400 406
401 static CounterNode* makeCounterNode(RenderObject* object, const AtomicString& id entifier, bool alwaysCreateCounter) 407 static CounterNode* makeCounterNode(RenderObject* object, const AtomicString& id entifier, bool alwaysCreateCounter)
402 { 408 {
403 ASSERT(object); 409 ASSERT(object);
(...skipping 301 matching lines...) Expand 10 before | Expand all | Expand 10 after
705 fprintf(stderr, " "); 711 fprintf(stderr, " ");
706 fprintf(stderr, "%p N:%p P:%p PS:%p NS:%p C:%p\n", 712 fprintf(stderr, "%p N:%p P:%p PS:%p NS:%p C:%p\n",
707 current, current->node(), current->parent(), current->previousSiblin g(), 713 current, current->node(), current->parent(), current->previousSiblin g(),
708 current->nextSibling(), current->m_hasCounterNodeMap? 714 current->nextSibling(), current->m_hasCounterNodeMap?
709 counterName ? WebCore::counterMaps().get(current)->get(identifier.im pl()).get() : (WebCore::CounterNode*)1 : (WebCore::CounterNode*)0); 715 counterName ? WebCore::counterMaps().get(current)->get(identifier.im pl()).get() : (WebCore::CounterNode*)1 : (WebCore::CounterNode*)0);
710 } 716 }
711 fflush(stderr); 717 fflush(stderr);
712 } 718 }
713 719
714 #endif // NDEBUG 720 #endif // NDEBUG
OLDNEW
« no previous file with comments | « LayoutTests/fast/css/counters/counter-after-style-crash-expected.txt ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698