Skip to content

Commit 8fa11b0

Browse files
committed
CQ. Simplify BufferedSink.
I don't believe that there are performance changes. These are mostly stylistic changes, and removing things like passing sink. Change-Id: I360f476407885694296d6c7693edc26492cf7e18 Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/416820 Reviewed-by: Paul Berry <[email protected]>
1 parent 331c700 commit 8fa11b0

File tree

7 files changed

+81
-101
lines changed

7 files changed

+81
-101
lines changed

pkg/analyzer/lib/src/dart/analysis/driver.dart

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1451,24 +1451,23 @@ class AnalysisDriver {
14511451

14521452
if (withFineDependencies && libraryRequirements != null) {
14531453
performance.run('writeResolvedLibrary', (_) {
1454-
var mapSink = BufferedSink(ByteSink());
1454+
var mapSink = BufferedSink();
14551455
mapSink.writeMap(
14561456
fileResultBytesMap,
14571457
writeKey: (uri) => mapSink.writeUri(uri),
14581458
writeValue: (bytes) => mapSink.writeUint8List(bytes),
14591459
);
1460-
var mapBytes = mapSink.flushAndTake();
1460+
var mapBytes = mapSink.takeBytes();
14611461

14621462
library.lastResolutionResult = LibraryResolutionResult(
14631463
requirements: libraryRequirements!,
14641464
bytes: mapBytes,
14651465
);
14661466

1467-
var byteSink = ByteSink();
1468-
var sink = BufferedSink(byteSink);
1467+
var sink = BufferedSink();
14691468
libraryRequirements.write(sink);
14701469
sink.writeUint8List(mapBytes);
1471-
var allBytes = sink.flushAndTake();
1470+
var allBytes = sink.takeBytes();
14721471

14731472
var key = library.resolvedKey;
14741473
_byteStore.putGet(key, allBytes);

pkg/analyzer/lib/src/dart/analysis/library_context.dart

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -535,8 +535,7 @@ class LinkedBundleProvider {
535535
required String key,
536536
required LinkedBundleEntry entry,
537537
}) {
538-
var byteSink = ByteSink();
539-
var sink = BufferedSink(byteSink);
538+
var sink = BufferedSink();
540539

541540
sink.writeStringUtf8(entry.apiSignature);
542541
sink.writeMap(
@@ -547,7 +546,7 @@ class LinkedBundleProvider {
547546
entry.requirements.write(sink);
548547
sink.writeUint8List(entry.linkedBytes);
549548

550-
var bytes = sink.flushAndTake();
549+
var bytes = sink.takeBytes();
551550
byteStore.putGet(key, bytes);
552551

553552
map[key] = entry;

pkg/analyzer/lib/src/dart/analysis/unlinked_data.dart

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -50,10 +50,9 @@ class AnalysisDriverUnlinkedUnit {
5050
}
5151

5252
Uint8List toBytes() {
53-
var byteSink = ByteSink();
54-
var sink = BufferedSink(byteSink);
53+
var sink = BufferedSink();
5554
write(sink);
56-
return sink.flushAndTake();
55+
return sink.takeBytes();
5756
}
5857

5958
void write(BufferedSink sink) {

pkg/analyzer/lib/src/summary2/bundle_writer.dart

Lines changed: 3 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -43,14 +43,12 @@ class BundleWriter {
4343
/// errors, or whether a parameter inherits `covariant`, or a class is
4444
/// simply bounded.
4545
late final _SummaryDataWriter _sink = _SummaryDataWriter(
46-
sink: ByteSink(),
4746
stringIndexer: _stringIndexer,
4847
);
4948

5049
/// The resolution sink - any data that references elements, so can only
5150
/// be read after elements are created and available via its [Reference]s.
5251
late final ResolutionSink _resolutionSink = ResolutionSink(
53-
sink: ByteSink(),
5452
stringIndexer: _stringIndexer,
5553
references: _references,
5654
);
@@ -70,7 +68,7 @@ class BundleWriter {
7068

7169
BundleWriterResult finish() {
7270
var baseResolutionOffset = _sink.offset;
73-
_sink.addBytes(_resolutionSink.flushAndTake());
71+
_sink.addBytes(_resolutionSink.takeBytes());
7472

7573
var librariesOffset = _sink.offset;
7674
_sink.writeList<_Library>(_libraries, (library) {
@@ -92,7 +90,7 @@ class BundleWriter {
9290
_sink.writeUInt32(referencesOffset);
9391
_sink.writeUInt32(stringTableOffset);
9492

95-
var bytes = _sink.flushAndTake();
93+
var bytes = _sink.takeBytes();
9694
return BundleWriterResult(
9795
resolutionBytes: bytes,
9896
);
@@ -718,7 +716,6 @@ class ResolutionSink extends _SummaryDataWriter {
718716
final _LocalElementIndexer localElements = _LocalElementIndexer();
719717

720718
ResolutionSink({
721-
required super.sink,
722719
required super.stringIndexer,
723720
required _BundleWriterReferences references,
724721
}) : _references = references;
@@ -1197,10 +1194,8 @@ class _SummaryDataWriter extends BufferedSink {
11971194
final StringIndexer _stringIndexer;
11981195

11991196
_SummaryDataWriter({
1200-
required ByteSink sink,
12011197
required StringIndexer stringIndexer,
1202-
}) : _stringIndexer = stringIndexer,
1203-
super(sink);
1198+
}) : _stringIndexer = stringIndexer;
12041199

12051200
void _writeFormalParameterKind(ParameterElement p) {
12061201
if (p.isRequiredPositional) {

pkg/analyzer/lib/src/summary2/data_writer.dart

Lines changed: 66 additions & 76 deletions
Original file line numberDiff line numberDiff line change
@@ -7,40 +7,36 @@ import 'dart:typed_data';
77

88
/// Puts a buffer in front of a [Sink<List<int>>].
99
class BufferedSink {
10-
static const int SIZE = 100000;
11-
static const int SAFE_SIZE = SIZE - 5;
12-
static const int SMALL = 10000;
10+
static const int _SIZE = 128 * 1024;
11+
static const int _SAFE_LENGTH = _SIZE - 5;
1312

14-
final ByteSink _sink;
13+
final BytesBuilder _builder = BytesBuilder(copy: false);
1514

16-
int flushedLength = 0;
17-
18-
Uint8List _buffer = Uint8List(SIZE);
19-
int length = 0;
15+
Uint8List _buffer = Uint8List(_SIZE);
16+
int _length = 0;
2017

2118
final Float64List _doubleBuffer = Float64List(1);
22-
Uint8List? _doubleBufferUint8;
19+
late final Uint8List _doubleBufferUint8 = _doubleBuffer.buffer.asUint8List();
2320

24-
BufferedSink(this._sink);
21+
BufferedSink();
2522

26-
int get offset => flushedLength + length;
23+
int get offset => _builder.length + _length;
2724

2825
@pragma("vm:prefer-inline")
2926
void addByte(int byte) {
30-
_buffer[length++] = byte;
31-
if (length == SIZE) {
32-
_sink.add(_buffer);
33-
_buffer = Uint8List(SIZE);
34-
length = 0;
35-
flushedLength += SIZE;
27+
_buffer[_length++] = byte;
28+
if (_length == _SIZE) {
29+
_builder.add(_buffer);
30+
_buffer = Uint8List(_SIZE);
31+
_length = 0;
3632
}
3733
}
3834

3935
@pragma("vm:prefer-inline")
4036
void addByte2(int byte1, int byte2) {
41-
if (length < SAFE_SIZE) {
42-
_buffer[length++] = byte1;
43-
_buffer[length++] = byte2;
37+
if (_length < _SAFE_LENGTH) {
38+
_buffer[_length++] = byte1;
39+
_buffer[_length++] = byte2;
4440
} else {
4541
addByte(byte1);
4642
addByte(byte2);
@@ -49,11 +45,11 @@ class BufferedSink {
4945

5046
@pragma("vm:prefer-inline")
5147
void addByte4(int byte1, int byte2, int byte3, int byte4) {
52-
if (length < SAFE_SIZE) {
53-
_buffer[length++] = byte1;
54-
_buffer[length++] = byte2;
55-
_buffer[length++] = byte3;
56-
_buffer[length++] = byte4;
48+
if (_length < _SAFE_LENGTH) {
49+
_buffer[_length++] = byte1;
50+
_buffer[_length++] = byte2;
51+
_buffer[_length++] = byte3;
52+
_buffer[_length++] = byte4;
5753
} else {
5854
addByte(byte1);
5955
addByte(byte2);
@@ -63,51 +59,58 @@ class BufferedSink {
6359
}
6460

6561
void addBytes(Uint8List bytes) {
66-
// Avoid copying a large buffer into the another large buffer. Also, if
67-
// the bytes buffer is too large to fit in our own buffer, just emit both.
68-
if (length + bytes.length < SIZE &&
69-
(bytes.length < SMALL || length < SMALL)) {
70-
_buffer.setRange(length, length + bytes.length, bytes);
71-
length += bytes.length;
72-
} else if (bytes.length < SMALL) {
73-
// Flush as much as we can in the current buffer.
74-
_buffer.setRange(length, SIZE, bytes);
75-
_sink.add(_buffer);
76-
// Copy over the remainder into a new buffer. It is guaranteed to fit
77-
// because the input byte array is small.
78-
int alreadyEmitted = SIZE - length;
79-
int remainder = bytes.length - alreadyEmitted;
80-
_buffer = Uint8List(SIZE);
81-
_buffer.setRange(0, remainder, bytes, alreadyEmitted);
82-
length = remainder;
83-
flushedLength += SIZE;
84-
} else {
85-
flush();
86-
_sink.add(bytes);
87-
flushedLength += bytes.length;
62+
if (bytes.isEmpty) {
63+
return;
64+
}
65+
66+
// Usually the bytes is short, and fits the current buffer.
67+
if (_length + bytes.length < _SIZE) {
68+
_buffer.setRange(_length, _length + bytes.length, bytes);
69+
_length += bytes.length;
70+
return;
8871
}
72+
73+
// If the bytes is too long, add separate buffers.
74+
if (bytes.length >= _SIZE) {
75+
_builder.add(_buffer.sublist(0, _length));
76+
_builder.add(bytes);
77+
// Start a new buffer.
78+
_buffer = Uint8List(_SIZE);
79+
_length = 0;
80+
return;
81+
}
82+
83+
// Copy as much as we can into the current buffer.
84+
_buffer.setRange(_length, _SIZE, bytes);
85+
_builder.add(_buffer);
86+
87+
// Copy the remainder into a new buffer.
88+
var alreadyCopied = _SIZE - _length;
89+
var remainder = bytes.length - alreadyCopied;
90+
_buffer = Uint8List(_SIZE);
91+
_buffer.setRange(0, remainder, bytes, alreadyCopied);
92+
_length = remainder;
8993
}
9094

9195
void addDouble(double value) {
92-
var doubleBufferUint8 =
93-
_doubleBufferUint8 ??= _doubleBuffer.buffer.asUint8List();
9496
_doubleBuffer[0] = value;
95-
addByte4(doubleBufferUint8[0], doubleBufferUint8[1], doubleBufferUint8[2],
96-
doubleBufferUint8[3]);
97-
addByte4(doubleBufferUint8[4], doubleBufferUint8[5], doubleBufferUint8[6],
98-
doubleBufferUint8[7]);
97+
addByte4(
98+
_doubleBufferUint8[0],
99+
_doubleBufferUint8[1],
100+
_doubleBufferUint8[2],
101+
_doubleBufferUint8[3],
102+
);
103+
addByte4(
104+
_doubleBufferUint8[4],
105+
_doubleBufferUint8[5],
106+
_doubleBufferUint8[6],
107+
_doubleBufferUint8[7],
108+
);
99109
}
100110

101-
void flush() {
102-
_sink.add(_buffer.sublist(0, length));
103-
_buffer = Uint8List(SIZE);
104-
flushedLength += length;
105-
length = 0;
106-
}
107-
108-
Uint8List flushAndTake() {
109-
_sink.add(_buffer.sublist(0, length));
110-
return _sink.builder.takeBytes();
111+
Uint8List takeBytes() {
112+
_builder.add(_buffer.sublist(0, _length));
113+
return _builder.takeBytes();
111114
}
112115

113116
@pragma("vm:prefer-inline")
@@ -258,16 +261,3 @@ class BufferedSink {
258261
writeStringUtf8(uriStr);
259262
}
260263
}
261-
262-
/// A [Sink] that directly writes data into a byte builder.
263-
class ByteSink implements Sink<List<int>> {
264-
final BytesBuilder builder = BytesBuilder(copy: false);
265-
266-
@override
267-
void add(List<int> data) {
268-
builder.add(data);
269-
}
270-
271-
@override
272-
void close() {}
273-
}

pkg/analyzer/lib/src/summary2/informative_data.dart

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -21,10 +21,9 @@ import 'package:analyzer/src/util/collection.dart';
2121
import 'package:analyzer/src/util/comment.dart';
2222

2323
Uint8List writeUnitInformative(CompilationUnit unit) {
24-
var byteSink = ByteSink();
25-
var sink = BufferedSink(byteSink);
24+
var sink = BufferedSink();
2625
_InformativeDataWriter(sink).write(unit);
27-
return sink.flushAndTake();
26+
return sink.takeBytes();
2827
}
2928

3029
/// We want to have actual offsets for tokens of various constants in the

pkg/analyzer/lib/src/summary2/package_bundle_format.dart

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -24,8 +24,7 @@ class PackageBundleBuilder {
2424
required Uint8List resolutionBytes,
2525
PackageBundleSdk? sdk,
2626
}) {
27-
var byteSink = ByteSink();
28-
var sink = BufferedSink(byteSink);
27+
var sink = BufferedSink();
2928

3029
if (sdk != null) {
3130
sink.writeByte(1);
@@ -44,7 +43,7 @@ class PackageBundleBuilder {
4443

4544
sink.writeUint8List(resolutionBytes);
4645

47-
return sink.flushAndTake();
46+
return sink.takeBytes();
4847
}
4948
}
5049

0 commit comments

Comments
 (0)