@samitouri / QOS-React-2 / commits / d3d2451a08

Use a single lane per priority level (#20791)

(Except transitions and retries.) The idea is that the only priorities that benefit from multiple parallel updates are the ones that might suspend: transitions and retries. All other priorities, including the ones that are interruptible like Continuous and Idle, don't need multiple lanes because it's better to batch everything together.

Andrew Clark committed Feb 10, 2021 at 18:09 UTC d3d2451a08c9afcc561f66383211ce2274d864e6
2 files changed +200 -190
packages/react-reconciler/src/ReactFiberLane.new.js
+100 -95
@@ -85,29 +85,40 @@ export const SyncLane: Lane = /* */ 0b0000000000000000000
85 export const SyncBatchedLane: Lane = /* */ 0b0000000000000000000000000000010;
86
87 export const InputDiscreteHydrationLane: Lane = /* */ 0b0000000000000000000000000000100;
88 -const InputDiscreteLanes: Lanes = /* */ 0b0000000000000000000000000011000;
88 +const InputDiscreteLane: Lanes = /* */ 0b0000000000000000000000000001000;
89
90 const InputContinuousHydrationLane: Lane = /* */ 0b0000000000000000000000000100000;
91 -const InputContinuousLanes: Lanes = /* */ 0b0000000000000000000000011000000;
91 +const InputContinuousLane: Lanes = /* */ 0b0000000000000000000000001000000;
92
93 export const DefaultHydrationLane: Lane = /* */ 0b0000000000000000000000100000000;
94 -export const DefaultLanes: Lanes = /* */ 0b0000000000000000000111000000000;
94 +export const DefaultLane: Lanes = /* */ 0b0000000000000000000001000000000;
95
96 const TransitionHydrationLane: Lane = /* */ 0b0000000000000000001000000000000;
97 const TransitionLanes: Lanes = /* */ 0b0000000001111111110000000000000;
98 -const FirstTransitionLane: Lane = /* */ 0b0000000000000000010000000000000;
98 +const TransitionLane1: Lane = /* */ 0b0000000000000000010000000000000;
99 +const TransitionLane2: Lane = /* */ 0b0000000000000000100000000000000;
100 +const TransitionLane3: Lane = /* */ 0b0000000000000001000000000000000;
101 +const TransitionLane4: Lane = /* */ 0b0000000000000010000000000000000;
102 +const TransitionLane5: Lane = /* */ 0b0000000000000100000000000000000;
103 +const TransitionLane6: Lane = /* */ 0b0000000000001000000000000000000;
104 +const TransitionLane7: Lane = /* */ 0b0000000000010000000000000000000;
105 +const TransitionLane8: Lane = /* */ 0b0000000000100000000000000000000;
106 +const TransitionLane9: Lane = /* */ 0b0000000001000000000000000000000;
107
108 const RetryLanes: Lanes = /* */ 0b0000011110000000000000000000000;
109 +const RetryLane1: Lane = /* */ 0b0000000010000000000000000000000;
110 +const RetryLane2: Lane = /* */ 0b0000000100000000000000000000000;
111 +const RetryLane3: Lane = /* */ 0b0000001000000000000000000000000;
112 +const RetryLane4: Lane = /* */ 0b0000010000000000000000000000000;
113
102 -const FirstRetryLane: Lanes = /* */ 0b0000000010000000000000000000000;
103 -export const SomeRetryLane: Lane = FirstRetryLane;
114 +export const SomeRetryLane: Lane = RetryLane1;
115
116 export const SelectiveHydrationLane: Lane = /* */ 0b0000100000000000000000000000000;
117
118 const NonIdleLanes = /* */ 0b0000111111111111111111111111111;
119
120 export const IdleHydrationLane: Lane = /* */ 0b0001000000000000000000000000000;
110 -const IdleLanes: Lanes = /* */ 0b0110000000000000000000000000000;
121 +const IdleLane: Lanes = /* */ 0b0010000000000000000000000000000;
122
123 export const OffscreenLane: Lane = /* */ 0b1000000000000000000000000000000;
124
@@ -115,8 +126,8 @@ export const NoTimestamp = -1;
126
127 let currentUpdateLanePriority: LanePriority = NoLanePriority;
128
118 -let nextTransitionLane: Lane = FirstTransitionLane;
119 -let nextRetryLane: Lane = FirstRetryLane;
129 +let nextTransitionLane: Lane = TransitionLane1;
130 +let nextRetryLane: Lane = RetryLane1;
131
132 export function getCurrentUpdateLanePriority(): LanePriority {
133 return currentUpdateLanePriority;
@@ -131,78 +142,73 @@ export function setCurrentUpdateLanePriority(newLanePriority: LanePriority) {
142 let return_highestLanePriority: LanePriority = DefaultLanePriority;
143
144 function getHighestPriorityLanes(lanes: Lanes | Lane): Lanes {
134 - if ((SyncLane & lanes) !== NoLanes) {
135 - return_highestLanePriority = SyncLanePriority;
136 - return SyncLane;
137 - }
138 - if ((SyncBatchedLane & lanes) !== NoLanes) {
139 - return_highestLanePriority = SyncBatchedLanePriority;
140 - return SyncBatchedLane;
141 - }
142 - if ((InputDiscreteHydrationLane & lanes) !== NoLanes) {
143 - return_highestLanePriority = InputDiscreteHydrationLanePriority;
144 - return InputDiscreteHydrationLane;
145 - }
146 - const inputDiscreteLanes = InputDiscreteLanes & lanes;
147 - if (inputDiscreteLanes !== NoLanes) {
148 - return_highestLanePriority = InputDiscreteLanePriority;
149 - return inputDiscreteLanes;
150 - }
151 - if ((lanes & InputContinuousHydrationLane) !== NoLanes) {
152 - return_highestLanePriority = InputContinuousHydrationLanePriority;
153 - return InputContinuousHydrationLane;
154 - }
155 - const inputContinuousLanes = InputContinuousLanes & lanes;
156 - if (inputContinuousLanes !== NoLanes) {
157 - return_highestLanePriority = InputContinuousLanePriority;
158 - return inputContinuousLanes;
159 - }
160 - if ((lanes & DefaultHydrationLane) !== NoLanes) {
161 - return_highestLanePriority = DefaultHydrationLanePriority;
162 - return DefaultHydrationLane;
163 - }
164 - const defaultLanes = DefaultLanes & lanes;
165 - if (defaultLanes !== NoLanes) {
166 - return_highestLanePriority = DefaultLanePriority;
167 - return defaultLanes;
168 - }
169 - if ((lanes & TransitionHydrationLane) !== NoLanes) {
170 - return_highestLanePriority = TransitionHydrationPriority;
171 - return TransitionHydrationLane;
172 - }
173 - const transitionLanes = TransitionLanes & lanes;
174 - if (transitionLanes !== NoLanes) {
175 - return_highestLanePriority = TransitionPriority;
176 - return transitionLanes;
177 - }
178 - const retryLanes = RetryLanes & lanes;
179 - if (retryLanes !== NoLanes) {
180 - return_highestLanePriority = RetryLanePriority;
181 - return retryLanes;
182 - }
183 - if (lanes & SelectiveHydrationLane) {
184 - return_highestLanePriority = SelectiveHydrationLanePriority;
185 - return SelectiveHydrationLane;
186 - }
187 - if ((lanes & IdleHydrationLane) !== NoLanes) {
188 - return_highestLanePriority = IdleHydrationLanePriority;
189 - return IdleHydrationLane;
190 - }
191 - const idleLanes = IdleLanes & lanes;
192 - if (idleLanes !== NoLanes) {
193 - return_highestLanePriority = IdleLanePriority;
194 - return idleLanes;
195 - }
196 - if ((OffscreenLane & lanes) !== NoLanes) {
197 - return_highestLanePriority = OffscreenLanePriority;
198 - return OffscreenLane;
199 - }
200 - if (__DEV__) {
201 - console.error('Should have found matching lanes. This is a bug in React.');
145 + switch (getHighestPriorityLane(lanes)) {
146 + case SyncLane:
147 + return_highestLanePriority = SyncLanePriority;
148 + return SyncLane;
149 + case SyncBatchedLane:
150 + return_highestLanePriority = SyncBatchedLanePriority;
151 + return SyncBatchedLane;
152 + case InputDiscreteHydrationLane:
153 + return_highestLanePriority = InputDiscreteHydrationLanePriority;
154 + return InputDiscreteHydrationLane;
155 + case InputDiscreteLane:
156 + return_highestLanePriority = InputDiscreteLanePriority;
157 + return InputDiscreteLane;
158 + case InputContinuousHydrationLane:
159 + return_highestLanePriority = InputContinuousHydrationLanePriority;
160 + return InputContinuousHydrationLane;
161 + case InputContinuousLane:
162 + return_highestLanePriority = InputContinuousLanePriority;
163 + return InputContinuousLane;
164 + case DefaultHydrationLane:
165 + return_highestLanePriority = DefaultHydrationLanePriority;
166 + return DefaultHydrationLane;
167 + case DefaultLane:
168 + return_highestLanePriority = DefaultLanePriority;
169 + return DefaultLane;
170 + case TransitionHydrationLane:
171 + return_highestLanePriority = TransitionHydrationPriority;
172 + return TransitionHydrationLane;
173 + case TransitionLane1:
174 + case TransitionLane2:
175 + case TransitionLane3:
176 + case TransitionLane4:
177 + case TransitionLane5:
178 + case TransitionLane6:
179 + case TransitionLane7:
180 + case TransitionLane8:
181 + case TransitionLane9:
182 + return_highestLanePriority = TransitionPriority;
183 + return lanes & TransitionLanes;
184 + case RetryLane1:
185 + case RetryLane2:
186 + case RetryLane3:
187 + case RetryLane4:
188 + return_highestLanePriority = RetryLanePriority;
189 + return lanes & RetryLanes;
190 + case SelectiveHydrationLane:
191 + return_highestLanePriority = SelectiveHydrationLanePriority;
192 + return SelectiveHydrationLane;
193 + case IdleHydrationLane:
194 + return_highestLanePriority = IdleHydrationLanePriority;
195 + return IdleHydrationLane;
196 + case IdleLane:
197 + return_highestLanePriority = IdleLanePriority;
198 + return IdleLane;
199 + case OffscreenLane:
200 + return_highestLanePriority = OffscreenLanePriority;
201 + return OffscreenLane;
202 + default:
203 + if (__DEV__) {
204 + console.error(
205 + 'Should have found matching lanes. This is a bug in React.',
206 + );
207 + }
208 + // This shouldn't be reachable, but as a fallback, return the entire bitmask.
209 + return_highestLanePriority = DefaultLanePriority;
210 + return lanes;
211 }
203 - // This shouldn't be reachable, but as a fallback, return the entire bitmask.
204 - return_highestLanePriority = DefaultLanePriority;
205 - return lanes;
212 }
213
214 export function schedulerPriorityToLanePriority(
@@ -516,20 +522,17 @@ export function findUpdateLane(lanePriority: LanePriority): Lane {
522 return SyncLane;
523 case SyncBatchedLanePriority:
524 return SyncBatchedLane;
519 - case InputDiscreteLanePriority: {
520 - return pickArbitraryLane(InputDiscreteLanes);
521 - }
522 - case InputContinuousLanePriority: {
523 - return pickArbitraryLane(InputContinuousLanes);
524 - }
525 - case DefaultLanePriority: {
526 - return pickArbitraryLane(DefaultLanes);
527 - }
525 + case InputDiscreteLanePriority:
526 + return InputDiscreteLane;
527 + case InputContinuousLanePriority:
528 + return InputContinuousLane;
529 + case DefaultLanePriority:
530 + return DefaultLane;
531 case TransitionPriority: // Should be handled by findTransitionLane instead
532 case RetryLanePriority: // Should be handled by findRetryLane instead
533 break;
534 case IdleLanePriority:
532 - return pickArbitraryLane(IdleLanes);
535 + return IdleLane;
536 default:
537 // The remaining priorities are not valid for updates
538 break;
@@ -549,7 +552,7 @@ export function claimNextTransitionLane(): Lane {
552 const lane = nextTransitionLane;
553 nextTransitionLane <<= 1;
554 if ((nextTransitionLane & TransitionLanes) === 0) {
552 - nextTransitionLane = FirstTransitionLane;
555 + nextTransitionLane = TransitionLane1;
556 }
557 return lane;
558 }
@@ -558,7 +561,7 @@ export function claimNextRetryLane(): Lane {
561 const lane = nextRetryLane;
562 nextRetryLane <<= 1;
563 if ((nextRetryLane & RetryLanes) === 0) {
561 - nextRetryLane = FirstRetryLane;
564 + nextRetryLane = RetryLane1;
565 }
566 return lane;
567 }
@@ -650,7 +653,7 @@ export function markRootUpdated(
653 // We don't do this if the incoming update is idle, because we never process
654 // idle updates until after all the regular updates have finished; there's no
655 // way it could unblock a transition.
653 - if ((updateLane & IdleLanes) === NoLanes) {
656 + if (updateLane !== IdleLane) {
657 root.suspendedLanes = NoLanes;
658 root.pingedLanes = NoLanes;
659 }
@@ -692,11 +695,13 @@ export function markRootExpired(root: FiberRoot, expiredLanes: Lanes) {
695 }
696
697 export function markDiscreteUpdatesExpired(root: FiberRoot) {
695 - root.expiredLanes |= InputDiscreteLanes & root.pendingLanes;
698 + if (root.pendingLanes & InputDiscreteLane) {
699 + root.expiredLanes |= InputDiscreteLane;
700 + }
701 }
702
703 export function hasDiscreteLanes(lanes: Lanes) {
699 - return (lanes & InputDiscreteLanes) !== NoLanes;
704 + return (lanes & InputDiscreteLane) !== NoLanes;
705 }
706
707 export function markRootMutableRead(root: FiberRoot, updateLane: Lane) {
packages/react-reconciler/src/ReactFiberLane.old.js
+100 -95
@@ -85,29 +85,40 @@ export const SyncLane: Lane = /* */ 0b0000000000000000000
85 export const SyncBatchedLane: Lane = /* */ 0b0000000000000000000000000000010;
86
87 export const InputDiscreteHydrationLane: Lane = /* */ 0b0000000000000000000000000000100;
88 -const InputDiscreteLanes: Lanes = /* */ 0b0000000000000000000000000011000;
88 +const InputDiscreteLane: Lanes = /* */ 0b0000000000000000000000000001000;
89
90 const InputContinuousHydrationLane: Lane = /* */ 0b0000000000000000000000000100000;
91 -const InputContinuousLanes: Lanes = /* */ 0b0000000000000000000000011000000;
91 +const InputContinuousLane: Lanes = /* */ 0b0000000000000000000000001000000;
92
93 export const DefaultHydrationLane: Lane = /* */ 0b0000000000000000000000100000000;
94 -export const DefaultLanes: Lanes = /* */ 0b0000000000000000000111000000000;
94 +export const DefaultLane: Lanes = /* */ 0b0000000000000000000001000000000;
95
96 const TransitionHydrationLane: Lane = /* */ 0b0000000000000000001000000000000;
97 const TransitionLanes: Lanes = /* */ 0b0000000001111111110000000000000;
98 -const FirstTransitionLane: Lane = /* */ 0b0000000000000000010000000000000;
98 +const TransitionLane1: Lane = /* */ 0b0000000000000000010000000000000;
99 +const TransitionLane2: Lane = /* */ 0b0000000000000000100000000000000;
100 +const TransitionLane3: Lane = /* */ 0b0000000000000001000000000000000;
101 +const TransitionLane4: Lane = /* */ 0b0000000000000010000000000000000;
102 +const TransitionLane5: Lane = /* */ 0b0000000000000100000000000000000;
103 +const TransitionLane6: Lane = /* */ 0b0000000000001000000000000000000;
104 +const TransitionLane7: Lane = /* */ 0b0000000000010000000000000000000;
105 +const TransitionLane8: Lane = /* */ 0b0000000000100000000000000000000;
106 +const TransitionLane9: Lane = /* */ 0b0000000001000000000000000000000;
107
108 const RetryLanes: Lanes = /* */ 0b0000011110000000000000000000000;
109 +const RetryLane1: Lane = /* */ 0b0000000010000000000000000000000;
110 +const RetryLane2: Lane = /* */ 0b0000000100000000000000000000000;
111 +const RetryLane3: Lane = /* */ 0b0000001000000000000000000000000;
112 +const RetryLane4: Lane = /* */ 0b0000010000000000000000000000000;
113
102 -const FirstRetryLane: Lanes = /* */ 0b0000000010000000000000000000000;
103 -export const SomeRetryLane: Lane = FirstRetryLane;
114 +export const SomeRetryLane: Lane = RetryLane1;
115
116 export const SelectiveHydrationLane: Lane = /* */ 0b0000100000000000000000000000000;
117
118 const NonIdleLanes = /* */ 0b0000111111111111111111111111111;
119
120 export const IdleHydrationLane: Lane = /* */ 0b0001000000000000000000000000000;
110 -const IdleLanes: Lanes = /* */ 0b0110000000000000000000000000000;
121 +const IdleLane: Lanes = /* */ 0b0010000000000000000000000000000;
122
123 export const OffscreenLane: Lane = /* */ 0b1000000000000000000000000000000;
124
@@ -115,8 +126,8 @@ export const NoTimestamp = -1;
126
127 let currentUpdateLanePriority: LanePriority = NoLanePriority;
128
118 -let nextTransitionLane: Lane = FirstTransitionLane;
119 -let nextRetryLane: Lane = FirstRetryLane;
129 +let nextTransitionLane: Lane = TransitionLane1;
130 +let nextRetryLane: Lane = RetryLane1;
131
132 export function getCurrentUpdateLanePriority(): LanePriority {
133 return currentUpdateLanePriority;
@@ -131,78 +142,73 @@ export function setCurrentUpdateLanePriority(newLanePriority: LanePriority) {
142 let return_highestLanePriority: LanePriority = DefaultLanePriority;
143
144 function getHighestPriorityLanes(lanes: Lanes | Lane): Lanes {
134 - if ((SyncLane & lanes) !== NoLanes) {
135 - return_highestLanePriority = SyncLanePriority;
136 - return SyncLane;
137 - }
138 - if ((SyncBatchedLane & lanes) !== NoLanes) {
139 - return_highestLanePriority = SyncBatchedLanePriority;
140 - return SyncBatchedLane;
141 - }
142 - if ((InputDiscreteHydrationLane & lanes) !== NoLanes) {
143 - return_highestLanePriority = InputDiscreteHydrationLanePriority;
144 - return InputDiscreteHydrationLane;
145 - }
146 - const inputDiscreteLanes = InputDiscreteLanes & lanes;
147 - if (inputDiscreteLanes !== NoLanes) {
148 - return_highestLanePriority = InputDiscreteLanePriority;
149 - return inputDiscreteLanes;
150 - }
151 - if ((lanes & InputContinuousHydrationLane) !== NoLanes) {
152 - return_highestLanePriority = InputContinuousHydrationLanePriority;
153 - return InputContinuousHydrationLane;
154 - }
155 - const inputContinuousLanes = InputContinuousLanes & lanes;
156 - if (inputContinuousLanes !== NoLanes) {
157 - return_highestLanePriority = InputContinuousLanePriority;
158 - return inputContinuousLanes;
159 - }
160 - if ((lanes & DefaultHydrationLane) !== NoLanes) {
161 - return_highestLanePriority = DefaultHydrationLanePriority;
162 - return DefaultHydrationLane;
163 - }
164 - const defaultLanes = DefaultLanes & lanes;
165 - if (defaultLanes !== NoLanes) {
166 - return_highestLanePriority = DefaultLanePriority;
167 - return defaultLanes;
168 - }
169 - if ((lanes & TransitionHydrationLane) !== NoLanes) {
170 - return_highestLanePriority = TransitionHydrationPriority;
171 - return TransitionHydrationLane;
172 - }
173 - const transitionLanes = TransitionLanes & lanes;
174 - if (transitionLanes !== NoLanes) {
175 - return_highestLanePriority = TransitionPriority;
176 - return transitionLanes;
177 - }
178 - const retryLanes = RetryLanes & lanes;
179 - if (retryLanes !== NoLanes) {
180 - return_highestLanePriority = RetryLanePriority;
181 - return retryLanes;
182 - }
183 - if (lanes & SelectiveHydrationLane) {
184 - return_highestLanePriority = SelectiveHydrationLanePriority;
185 - return SelectiveHydrationLane;
186 - }
187 - if ((lanes & IdleHydrationLane) !== NoLanes) {
188 - return_highestLanePriority = IdleHydrationLanePriority;
189 - return IdleHydrationLane;
190 - }
191 - const idleLanes = IdleLanes & lanes;
192 - if (idleLanes !== NoLanes) {
193 - return_highestLanePriority = IdleLanePriority;
194 - return idleLanes;
195 - }
196 - if ((OffscreenLane & lanes) !== NoLanes) {
197 - return_highestLanePriority = OffscreenLanePriority;
198 - return OffscreenLane;
199 - }
200 - if (__DEV__) {
201 - console.error('Should have found matching lanes. This is a bug in React.');
145 + switch (getHighestPriorityLane(lanes)) {
146 + case SyncLane:
147 + return_highestLanePriority = SyncLanePriority;
148 + return SyncLane;
149 + case SyncBatchedLane:
150 + return_highestLanePriority = SyncBatchedLanePriority;
151 + return SyncBatchedLane;
152 + case InputDiscreteHydrationLane:
153 + return_highestLanePriority = InputDiscreteHydrationLanePriority;
154 + return InputDiscreteHydrationLane;
155 + case InputDiscreteLane:
156 + return_highestLanePriority = InputDiscreteLanePriority;
157 + return InputDiscreteLane;
158 + case InputContinuousHydrationLane:
159 + return_highestLanePriority = InputContinuousHydrationLanePriority;
160 + return InputContinuousHydrationLane;
161 + case InputContinuousLane:
162 + return_highestLanePriority = InputContinuousLanePriority;
163 + return InputContinuousLane;
164 + case DefaultHydrationLane:
165 + return_highestLanePriority = DefaultHydrationLanePriority;
166 + return DefaultHydrationLane;
167 + case DefaultLane:
168 + return_highestLanePriority = DefaultLanePriority;
169 + return DefaultLane;
170 + case TransitionHydrationLane:
171 + return_highestLanePriority = TransitionHydrationPriority;
172 + return TransitionHydrationLane;
173 + case TransitionLane1:
174 + case TransitionLane2:
175 + case TransitionLane3:
176 + case TransitionLane4:
177 + case TransitionLane5:
178 + case TransitionLane6:
179 + case TransitionLane7:
180 + case TransitionLane8:
181 + case TransitionLane9:
182 + return_highestLanePriority = TransitionPriority;
183 + return lanes & TransitionLanes;
184 + case RetryLane1:
185 + case RetryLane2:
186 + case RetryLane3:
187 + case RetryLane4:
188 + return_highestLanePriority = RetryLanePriority;
189 + return lanes & RetryLanes;
190 + case SelectiveHydrationLane:
191 + return_highestLanePriority = SelectiveHydrationLanePriority;
192 + return SelectiveHydrationLane;
193 + case IdleHydrationLane:
194 + return_highestLanePriority = IdleHydrationLanePriority;
195 + return IdleHydrationLane;
196 + case IdleLane:
197 + return_highestLanePriority = IdleLanePriority;
198 + return IdleLane;
199 + case OffscreenLane:
200 + return_highestLanePriority = OffscreenLanePriority;
201 + return OffscreenLane;
202 + default:
203 + if (__DEV__) {
204 + console.error(
205 + 'Should have found matching lanes. This is a bug in React.',
206 + );
207 + }
208 + // This shouldn't be reachable, but as a fallback, return the entire bitmask.
209 + return_highestLanePriority = DefaultLanePriority;
210 + return lanes;
211 }
203 - // This shouldn't be reachable, but as a fallback, return the entire bitmask.
204 - return_highestLanePriority = DefaultLanePriority;
205 - return lanes;
212 }
213
214 export function schedulerPriorityToLanePriority(
@@ -516,20 +522,17 @@ export function findUpdateLane(lanePriority: LanePriority): Lane {
522 return SyncLane;
523 case SyncBatchedLanePriority:
524 return SyncBatchedLane;
519 - case InputDiscreteLanePriority: {
520 - return pickArbitraryLane(InputDiscreteLanes);
521 - }
522 - case InputContinuousLanePriority: {
523 - return pickArbitraryLane(InputContinuousLanes);
524 - }
525 - case DefaultLanePriority: {
526 - return pickArbitraryLane(DefaultLanes);
527 - }
525 + case InputDiscreteLanePriority:
526 + return InputDiscreteLane;
527 + case InputContinuousLanePriority:
528 + return InputContinuousLane;
529 + case DefaultLanePriority:
530 + return DefaultLane;
531 case TransitionPriority: // Should be handled by findTransitionLane instead
532 case RetryLanePriority: // Should be handled by findRetryLane instead
533 break;
534 case IdleLanePriority:
532 - return pickArbitraryLane(IdleLanes);
535 + return IdleLane;
536 default:
537 // The remaining priorities are not valid for updates
538 break;
@@ -549,7 +552,7 @@ export function claimNextTransitionLane(): Lane {
552 const lane = nextTransitionLane;
553 nextTransitionLane <<= 1;
554 if ((nextTransitionLane & TransitionLanes) === 0) {
552 - nextTransitionLane = FirstTransitionLane;
555 + nextTransitionLane = TransitionLane1;
556 }
557 return lane;
558 }
@@ -558,7 +561,7 @@ export function claimNextRetryLane(): Lane {
561 const lane = nextRetryLane;
562 nextRetryLane <<= 1;
563 if ((nextRetryLane & RetryLanes) === 0) {
561 - nextRetryLane = FirstRetryLane;
564 + nextRetryLane = RetryLane1;
565 }
566 return lane;
567 }
@@ -650,7 +653,7 @@ export function markRootUpdated(
653 // We don't do this if the incoming update is idle, because we never process
654 // idle updates until after all the regular updates have finished; there's no
655 // way it could unblock a transition.
653 - if ((updateLane & IdleLanes) === NoLanes) {
656 + if (updateLane !== IdleLane) {
657 root.suspendedLanes = NoLanes;
658 root.pingedLanes = NoLanes;
659 }
@@ -692,11 +695,13 @@ export function markRootExpired(root: FiberRoot, expiredLanes: Lanes) {
695 }
696
697 export function markDiscreteUpdatesExpired(root: FiberRoot) {
695 - root.expiredLanes |= InputDiscreteLanes & root.pendingLanes;
698 + if (root.pendingLanes & InputDiscreteLane) {
699 + root.expiredLanes |= InputDiscreteLane;
700 + }
701 }
702
703 export function hasDiscreteLanes(lanes: Lanes) {
699 - return (lanes & InputDiscreteLanes) !== NoLanes;
704 + return (lanes & InputDiscreteLane) !== NoLanes;
705 }
706
707 export function markRootMutableRead(root: FiberRoot, updateLane: Lane) {