| /* |
| * Copyright 2024 Google LLC |
| * |
| * Use of this source code is governed by a BSD-style license that can be |
| * found in the LICENSE file. |
| */ |
| |
| #include "src/sksl/codegen/SkSLWGSLValidator.h" |
| |
| #include "src/sksl/SkSLErrorReporter.h" |
| #include "src/sksl/SkSLPosition.h" |
| |
| #include "src/tint/lang/wgsl/enums.h" |
| #include "src/tint/lang/wgsl/reader/options.h" |
| #include "tint/tint.h" |
| |
| namespace SkSL { |
| |
| static bool validate_wgsl(ErrorReporter& reporter, |
| std::string_view wgsl, |
| bool appendError, |
| std::string* warnings) { |
| // Enable the WGSL optional features that Skia might rely on. |
| tint::wgsl::reader::Options options; |
| for (auto extension : {tint::wgsl::Extension::kChromiumExperimentalPixelLocal, |
| tint::wgsl::Extension::kDualSourceBlending}) { |
| options.allowed_features.extensions.insert(extension); |
| } |
| options.allowed_features.features.insert( |
| tint::wgsl::LanguageFeature::kUnrestrictedPointerParameters); |
| |
| // Verify that the WGSL we produced is valid. |
| tint::Source::File srcFile("", wgsl); |
| tint::Program program(tint::wgsl::reader::Parse(&srcFile, options)); |
| |
| if (program.Diagnostics().ContainsErrors()) { |
| // The program isn't valid WGSL. |
| if (appendError) { |
| // Report the error via SkDEBUGFAIL and append the generated program for |
| // ease of debugging. We don't do this for our golden test output because |
| // it can change too often |
| tint::diag::Formatter diagFormatter; |
| std::string diagOutput = diagFormatter.Format(program.Diagnostics()).Plain(); |
| diagOutput += "\n"; |
| diagOutput += wgsl; |
| SkDEBUGFAILF("%s", diagOutput.c_str()); |
| } else { |
| reporter.error(Position(), |
| std::string("Tint compilation failed.\n\n") + std::string(wgsl)); |
| } |
| return false; |
| } |
| |
| if (!program.Diagnostics().empty()) { |
| // The program contains warnings. Report them as-is. |
| tint::diag::Formatter diagFormatter; |
| *warnings = diagFormatter.Format(program.Diagnostics()).Plain(); |
| } |
| return true; |
| } |
| |
| bool ValidateWGSL(ErrorReporter& reporter, std::string_view wgsl, std::string* warnings) { |
| return validate_wgsl(reporter, wgsl, false, warnings); |
| } |
| |
| bool ValidateWGSLVerbose(ErrorReporter& reporter, std::string_view wgsl, std::string* warnings) { |
| return validate_wgsl(reporter, wgsl, true, warnings); |
| } |
| |
| } // namespace SkSL |