blob: 200db5c9ba97f67740194d491bc419f2f70461af [file] [log] [blame]
/*
* Copyright 2022 Google Inc.
*
* Use of this source code is governed by a BSD-style license that can be
* found in the LICENSE file.
*/
#include "src/core/SkArenaAlloc.h"
#include "src/core/SkOpts.h"
#include "src/core/SkRasterPipeline.h"
#include "src/sksl/codegen/SkSLRasterPipelineBuilder.h"
#include "tests/Test.h"
struct TestingOnly_SkRasterPipelineInspector {
using StageList = SkRasterPipeline::StageList;
static StageList* GetStageList(SkRasterPipeline* p) { return p->fStages; }
};
static SkSL::RP::SlotRange two_slots_at(SkSL::RP::Slot index) {
return SkSL::RP::SlotRange{index, 2};
}
static SkSL::RP::SlotRange four_slots_at(SkSL::RP::Slot index) {
return SkSL::RP::SlotRange{index, 4};
}
DEF_TEST(RasterPipelineBuilder, r) {
// Create a very simple nonsense program.
SkSL::RP::Builder builder;
builder.store_src_rg(two_slots_at(0));
builder.store_src(four_slots_at(2));
builder.store_dst(four_slots_at(6));
builder.load_src(four_slots_at(1));
builder.load_dst(four_slots_at(3));
SkSL::RP::Program program = builder.finish();
// Instantiate this program.
SkArenaAlloc alloc(/*firstHeapAllocation=*/1000);
SkRasterPipeline pipeline(&alloc);
program.appendStages(&pipeline, &alloc);
// Double check that the resulting stage list contains the correct ops.
// (Note that the RasterPipeline stage list is stored in backwards order.)
const auto* stages = TestingOnly_SkRasterPipelineInspector::GetStageList(&pipeline);
REPORTER_ASSERT(r, stages->stage == SkRasterPipeline::load_dst);
stages = stages->prev;
REPORTER_ASSERT(r, stages->stage == SkRasterPipeline::load_src);
stages = stages->prev;
REPORTER_ASSERT(r, stages->stage == SkRasterPipeline::store_dst);
stages = stages->prev;
REPORTER_ASSERT(r, stages->stage == SkRasterPipeline::store_src);
stages = stages->prev;
REPORTER_ASSERT(r, stages->stage == SkRasterPipeline::store_src_rg);
// Double check that the resulting stage list contains the correct context pointers.
// All of the ops here hold a pointer directly to their associated slot, and slots are always
// assigned contiguously and in order, and never rearranged. We should be able to verify that
// they are all where we expect them to be.
const auto* firstStage = stages;
const float* slot0 = (const float*)firstStage->ctx;
const int N = SkOpts::raster_pipeline_highp_stride;
stages = TestingOnly_SkRasterPipelineInspector::GetStageList(&pipeline);
REPORTER_ASSERT(r, stages->ctx == slot0 + (3 * N));
stages = stages->prev;
REPORTER_ASSERT(r, stages->ctx == slot0 + (1 * N));
stages = stages->prev;
REPORTER_ASSERT(r, stages->ctx == slot0 + (6 * N));
stages = stages->prev;
REPORTER_ASSERT(r, stages->ctx == slot0 + (2 * N));
stages = stages->prev;
REPORTER_ASSERT(r, stages->ctx == slot0 + (0 * N));
}