Commit 120589bd authored by Morten Stenshorne's avatar Morten Stenshorne Committed by Commit Bot

[LayoutNG] Remove NGInlineChildLayoutContext member.

Remove NGInlineChildLayoutContext from NGBlockLayoutAlgorithm. This structure
is quite big, and since we stack-allocate the alogorithms, this matters. Only
stack-allocate NGInlineChildLayoutContext on demand (when children are inline).

This saves 816 bytes [*] of stack space per in-flow layout recursion.

[*] Linux 64bit release.

Bug: 930637
Change-Id: I40c12cb6e7996e54c9bf3ebe7285350591c90fef
Reviewed-on: https://chromium-review.googlesource.com/c/1485238Reviewed-by: default avatarIan Kilpatrick <ikilpatrick@chromium.org>
Reviewed-by: default avatarChristian Biesinger <cbiesinger@chromium.org>
Reviewed-by: default avatarKoji Ishii <kojii@chromium.org>
Commit-Queue: Morten Stenshorne <mstensho@chromium.org>
Cr-Commit-Position: refs/heads/master@{#635150}
parent 02c469f4
......@@ -353,6 +353,22 @@ NGLogicalOffset NGBlockLayoutAlgorithm::CalculateLogicalOffset(
}
scoped_refptr<const NGLayoutResult> NGBlockLayoutAlgorithm::Layout() {
// Inline children require an inline child layout context to be
// passed between siblings. We want to stack-allocate that one, but
// only on demand, as it's quite big.
if (Node().ChildrenInline())
return LayoutWithInlineChildLayoutContext();
return Layout(nullptr);
}
NOINLINE scoped_refptr<const NGLayoutResult>
NGBlockLayoutAlgorithm::LayoutWithInlineChildLayoutContext() {
NGInlineChildLayoutContext context;
return Layout(&context);
}
inline scoped_refptr<const NGLayoutResult> NGBlockLayoutAlgorithm::Layout(
NGInlineChildLayoutContext* inline_child_layout_context) {
NGBoxStrut borders = ComputeBorders(ConstraintSpace(), Node());
NGBoxStrut padding = ComputePadding(ConstraintSpace(), Style());
border_padding_ = borders + padding;
......@@ -529,9 +545,9 @@ scoped_refptr<const NGLayoutResult> NGBlockLayoutAlgorithm::Layout() {
&previous_inflow_position);
previous_inline_break_token = nullptr;
} else {
abort =
!HandleInflow(child, child_break_token, &previous_inflow_position,
&previous_inline_break_token);
abort = !HandleInflow(
child, child_break_token, &previous_inflow_position,
inline_child_layout_context, &previous_inline_break_token);
}
if (abort) {
......@@ -1218,6 +1234,7 @@ bool NGBlockLayoutAlgorithm::HandleInflow(
NGLayoutInputNode child,
const NGBreakToken* child_break_token,
NGPreviousInflowPosition* previous_inflow_position,
NGInlineChildLayoutContext* inline_child_layout_context,
scoped_refptr<const NGInlineBreakToken>* previous_inline_break_token) {
DCHECK(child);
DCHECK(!child.IsFloating());
......@@ -1261,15 +1278,16 @@ bool NGBlockLayoutAlgorithm::HandleInflow(
has_clearance_past_adjoining_floats, /* is_new_fc */ false);
NGConstraintSpace child_space =
CreateConstraintSpaceForChild(child, child_data, child_available_size_);
scoped_refptr<const NGLayoutResult> layout_result = child.Layout(
child_space, child_break_token, &inline_child_layout_context_);
scoped_refptr<const NGLayoutResult> layout_result =
child.Layout(child_space, child_break_token, inline_child_layout_context);
// To save space of the stack when we recurse into |NGBlockNode::Layout|
// above, the rest of this function is continued within |FinishInflow|.
// However it should be read as one function.
return FinishInflow(child, child_break_token, child_space,
std::move(layout_result), &child_data,
previous_inflow_position, previous_inline_break_token);
previous_inflow_position, inline_child_layout_context,
previous_inline_break_token);
}
bool NGBlockLayoutAlgorithm::FinishInflow(
......@@ -1279,6 +1297,7 @@ bool NGBlockLayoutAlgorithm::FinishInflow(
scoped_refptr<const NGLayoutResult> layout_result,
NGInflowChildData* child_data,
NGPreviousInflowPosition* previous_inflow_position,
NGInlineChildLayoutContext* inline_child_layout_context,
scoped_refptr<const NGInlineBreakToken>* previous_inline_break_token) {
base::Optional<LayoutUnit> child_bfc_block_offset =
layout_result->BfcBlockOffset();
......@@ -1406,7 +1425,7 @@ bool NGBlockLayoutAlgorithm::FinishInflow(
NGConstraintSpace new_child_space = CreateConstraintSpaceForChild(
child, *child_data, child_available_size_, child_bfc_block_offset);
layout_result = child.Layout(new_child_space, child_break_token,
&inline_child_layout_context_);
inline_child_layout_context);
if (layout_result->Status() == NGLayoutResult::kBfcBlockOffsetResolved) {
// Even a second layout pass may abort, if the BFC block offset initially
......@@ -1419,7 +1438,7 @@ bool NGBlockLayoutAlgorithm::FinishInflow(
new_child_space = CreateConstraintSpaceForChild(
child, *child_data, child_available_size_, child_bfc_block_offset);
layout_result = child.Layout(new_child_space, child_break_token,
&inline_child_layout_context_);
inline_child_layout_context);
}
DCHECK_EQ(layout_result->Status(), NGLayoutResult::kSuccess);
......
......@@ -68,6 +68,12 @@ class CORE_EXPORT NGBlockLayoutAlgorithm
scoped_refptr<const NGLayoutResult> Layout() override;
private:
NOINLINE scoped_refptr<const NGLayoutResult>
LayoutWithInlineChildLayoutContext();
inline scoped_refptr<const NGLayoutResult> Layout(
NGInlineChildLayoutContext* inline_child_layout_context);
// Return the BFC block offset of this block.
LayoutUnit BfcBlockOffset() const {
// If we have resolved our BFC block offset, use that.
......@@ -183,6 +189,7 @@ class CORE_EXPORT NGBlockLayoutAlgorithm
NGLayoutInputNode child,
const NGBreakToken* child_break_token,
NGPreviousInflowPosition*,
NGInlineChildLayoutContext*,
scoped_refptr<const NGInlineBreakToken>* previous_inline_break_token);
bool FinishInflow(
......@@ -192,6 +199,7 @@ class CORE_EXPORT NGBlockLayoutAlgorithm
scoped_refptr<const NGLayoutResult>,
NGInflowChildData*,
NGPreviousInflowPosition*,
NGInlineChildLayoutContext*,
scoped_refptr<const NGInlineBreakToken>* previous_inline_break_token);
// Return the amount of block space available in the current fragmentainer
......@@ -297,8 +305,6 @@ class CORE_EXPORT NGBlockLayoutAlgorithm
NGBoxStrut border_scrollbar_padding_;
LayoutUnit intrinsic_block_size_;
NGInlineChildLayoutContext inline_child_layout_context_;
// The line box index at which we ran out of space. This where we'll actually
// end up breaking, unless we determine that we should break earlier in order
// to satisfy the widows request.
......
......@@ -838,6 +838,12 @@ void NGBlockNode::CopyFragmentDataToLayoutBoxForInlineChildren(
}
}
bool NGBlockNode::ChildrenInline() const {
if (const auto* block = ToLayoutBlockFlowOrNull(box_))
return AreNGBlockFlowChildrenInline(block);
return false;
}
bool NGBlockNode::IsInlineLevel() const {
return GetLayoutBox()->IsInline();
}
......
......@@ -69,6 +69,7 @@ class CORE_EXPORT NGBlockNode final : public NGLayoutInputNode {
NGBlockNode GetRenderedLegend() const;
NGBlockNode GetFieldsetContent() const;
bool ChildrenInline() const;
bool IsInlineLevel() const;
bool IsAtomicInlineLevel() const;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment