Add support for int-typed data payloads.
If we are going to create a new snippet ID every time a runtime effect
is painted, we will overflow a byte very rapidly.
Change-Id: Ic094af2a81e590488bf90b60492b004e9135d4a2
Bug: skia:13405
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/551843
Commit-Queue: John Stiles <johnstiles@google.com>
Auto-Submit: John Stiles <johnstiles@google.com>
Reviewed-by: Robert Phillips <robertphillips@google.com>
diff --git a/src/core/SkPaintParamsKey.cpp b/src/core/SkPaintParamsKey.cpp
index 8f5e3b3..521366d 100644
--- a/src/core/SkPaintParamsKey.cpp
+++ b/src/core/SkPaintParamsKey.cpp
@@ -140,24 +140,19 @@
}
#endif // SK_DEBUG
-void SkPaintParamsKeyBuilder::addBytes(uint32_t numBytes, const uint8_t* data) {
- if (!this->isValid()) {
- return;
+static int field_size(DataPayloadType type) {
+ switch (type) {
+ case DataPayloadType::kByte:
+ case DataPayloadType::kPointerIndex: return 1;
+ case DataPayloadType::kInt: return 4;
+ case DataPayloadType::kFloat4: return 16;
}
-
- if (fStack.empty()) {
- // SKGPU_LOG_W("Missing call to 'beginBlock'.");
- this->makeInvalid();
- return;
- }
-
- SkDEBUGCODE(this->checkExpectations(DataPayloadType::kByte, numBytes);)
- SkASSERT(!this->isLocked());
-
- fData.append(numBytes, data);
+ SkUNREACHABLE;
}
-void SkPaintParamsKeyBuilder::add(int numColors, const SkColor4f* color) {
+void SkPaintParamsKeyBuilder::addToKey(uint32_t count,
+ const void* data,
+ DataPayloadType payloadType) {
if (!this->isValid()) {
return;
}
@@ -168,27 +163,29 @@
return;
}
- SkDEBUGCODE(this->checkExpectations(DataPayloadType::kFloat4, numColors);)
+ SkDEBUGCODE(this->checkExpectations(payloadType, count);)
SkASSERT(!this->isLocked());
- fData.append(16 * numColors, reinterpret_cast<const uint8_t*>(color));
+ fData.append(field_size(payloadType) * count, reinterpret_cast<const uint8_t*>(data));
+}
+
+void SkPaintParamsKeyBuilder::addBytes(uint32_t numBytes, const uint8_t* data) {
+ this->addToKey(numBytes, data, DataPayloadType::kByte);
+}
+
+void SkPaintParamsKeyBuilder::addInts(uint32_t numInts, const int32_t* data) {
+ this->addToKey(numInts, data, DataPayloadType::kInt);
+}
+
+void SkPaintParamsKeyBuilder::add(int numColors, const SkColor4f* colors) {
+ this->addToKey(numColors, colors, DataPayloadType::kFloat4);
}
void SkPaintParamsKeyBuilder::addPointer(const void* ptr) {
- if (!this->isValid()) {
- return;
- }
-
- if (fStack.empty()) {
- // SKGPU_LOG_W("Missing call to 'beginBlock'.");
- this->makeInvalid();
- return;
- }
-
- SkDEBUGCODE(this->checkExpectations(SkPaintParamsKey::DataPayloadType::kPointerIndex, 1);)
- SkASSERT(!this->isLocked());
SkASSERT(fPointerData.size() <= 0xFF);
- fData.push_back((uint8_t)fPointerData.size());
+ uint8_t pointerIndex = (uint8_t)fPointerData.size();
+
+ this->addToKey(1, &pointerIndex, DataPayloadType::kPointerIndex);
fPointerData.push_back(ptr);
}
@@ -369,19 +366,10 @@
return fBlock.subspan(payloadOffset, payloadSize);
}
-static int field_size(const DataPayloadField& field) {
- switch (field.fType) {
- case DataPayloadType::kByte:
- case DataPayloadType::kPointerIndex: return field.fCount;
- case DataPayloadType::kFloat4: return field.fCount * 16;
- }
- SkUNREACHABLE;
-}
-
static int field_offset(SkSpan<const DataPayloadField> fields, int fieldIndex) {
int byteOffset = 0;
for (int i = 0; i < fieldIndex; ++i) {
- byteOffset += field_size(fields[i]);
+ byteOffset += field_size(fields[i].fType) * fields[i].fCount;
}
return byteOffset;
}
@@ -401,6 +389,13 @@
fieldIndex);
}
+SkSpan<const int32_t> SkPaintParamsKey::BlockReader::ints(int fieldIndex) const {
+ SkASSERT(fEntry->fDataPayloadExpectations[fieldIndex].fType == DataPayloadType::kInt);
+ return payload_subspan_for_field<int32_t>(this->dataPayload(),
+ fEntry->fDataPayloadExpectations,
+ fieldIndex);
+}
+
SkSpan<const SkColor4f> SkPaintParamsKey::BlockReader::colors(int fieldIndex) const {
SkASSERT(fEntry->fDataPayloadExpectations[fieldIndex].fType == DataPayloadType::kFloat4);
return payload_subspan_for_field<SkColor4f>(this->dataPayload(),
diff --git a/src/core/SkPaintParamsKey.h b/src/core/SkPaintParamsKey.h
index 3dfee18..6a09fed 100644
--- a/src/core/SkPaintParamsKey.h
+++ b/src/core/SkPaintParamsKey.h
@@ -54,6 +54,7 @@
enum class DataPayloadType {
kByte,
+ kInt,
kFloat4,
// Represents a position inside the fPointerData span.
kPointerIndex,
@@ -86,6 +87,7 @@
// Retrieve the fieldIndex-th field in the data payload as a span. The type being read
// is checked against the data payload's structure.
SkSpan<const uint8_t> bytes(int fieldIndex) const;
+ SkSpan<const int32_t> ints(int fieldIndex) const;
SkSpan<const SkColor4f> colors(int fieldIndex) const;
const void* pointer(int fieldIndex) const;
@@ -209,7 +211,11 @@
void addByte(uint8_t data) {
this->addBytes(1, &data);
}
- void add(int numColors, const SkColor4f* color);
+ void addInts(uint32_t numInts, const int32_t* data);
+ void addInt(int32_t data) {
+ this->addInts(1, &data);
+ }
+ void add(int numColors, const SkColor4f* colors);
void add(const SkColor4f& color) {
this->add(/*numColors=*/1, &color);
}
@@ -252,6 +258,7 @@
SkDEBUGCODE(bool isLocked() const { return fLocked; })
private:
+ void addToKey(uint32_t count, const void* data, SkPaintParamsKey::DataPayloadType payloadType);
void makeInvalid();
#ifdef SK_DEBUG
diff --git a/tests/graphite/KeyTest.cpp b/tests/graphite/KeyTest.cpp
index 65a4d4b..88c1b25 100644
--- a/tests/graphite/KeyTest.cpp
+++ b/tests/graphite/KeyTest.cpp
@@ -190,20 +190,20 @@
static constexpr SkPaintParamsKey::DataPayloadField kDataFields[] = {
{"ByteX", SkPaintParamsKey::DataPayloadType::kByte, kCountX},
{"Float4Y", SkPaintParamsKey::DataPayloadType::kFloat4, kCountY},
- {"ByteZ", SkPaintParamsKey::DataPayloadType::kByte, kCountZ},
+ {"IntZ", SkPaintParamsKey::DataPayloadType::kInt, kCountZ},
};
int userSnippetID = dict->addUserDefinedSnippet("key", kDataFields);
static constexpr uint8_t kDataX[kCountX] = {1, 2, 3};
static constexpr SkColor4f kDataY[kCountY] = {{4, 5, 6, 7}, {8, 9, 10, 11}};
- static constexpr uint8_t kDataZ[kCountZ] = {12, 13, 14, 15, 16, 17, 18};
+ static constexpr int32_t kDataZ[kCountZ] = {-1234567, 13, 14, 15, 16, 17, 7654321};
SkPaintParamsKeyBuilder builder(dict, SkBackend::kGraphite);
builder.beginBlock(userSnippetID);
builder.addBytes(kCountX, kDataX);
builder.add (kCountY, kDataY);
- builder.addBytes(kCountZ, kDataZ);
+ builder.addInts (kCountZ, kDataZ);
builder.endBlock();
SkPaintParamsKey key = builder.lockAsKey();
@@ -222,7 +222,7 @@
REPORTER_ASSERT(reporter, readerDataY.size() == kCountY);
REPORTER_ASSERT(reporter, 0 == memcmp(readerDataY.data(), kDataY, sizeof(kDataY)));
- SkSpan<const uint8_t> readerBytesZ = reader.bytes(2);
+ SkSpan<const int32_t> readerBytesZ = reader.ints(2);
REPORTER_ASSERT(reporter, readerBytesZ.size() == kCountZ);
REPORTER_ASSERT(reporter, 0 == memcmp(readerBytesZ.data(), kDataZ, sizeof(kDataZ)));
}