static void handle_cmd(struct android_app* app, int32_t cmd) { struct VisualBenchState* state = (struct VisualBenchState*)app->userData; switch (cmd) { case APP_CMD_INIT_WINDOW: // The window is being shown, get it ready. if (state->fApp->window != nullptr && kInit_State == state->fState) { // drain any events that occurred before |window| was assigned. while (SkEvent::ProcessEvent()); // Start normal Skia sequence application_init(); SkTArray<const char*> args; args.push_back("VisualBench"); for (int i = 0; i < state->fFlags.count(); i++) { SkDebugf(state->fFlags[i].c_str()); args.push_back(state->fFlags[i].c_str()); } state->fWindow = create_sk_window((void*)state->fApp->window, args.count(), const_cast<char**>(args.begin())); state->fWindow->forceInvalAll(); state->fState = kAnimate_State; } break; case APP_CMD_TERM_WINDOW: state->fState = kDestroyRequested_State; break; } }
void SkDiffContext::diffPatterns(const char baselinePattern[], const char testPattern[]) { // Get the files in the baseline and test patterns. Because they are in sorted order, it's easy // to find corresponding images by matching entry indices. SkTArray<SkString> baselineEntries; if (!glob_files(baselinePattern, &baselineEntries)) { SkDebugf("Unable to get pattern \"%s\"\n", baselinePattern); return; } SkTArray<SkString> testEntries; if (!glob_files(testPattern, &testEntries)) { SkDebugf("Unable to get pattern \"%s\"\n", testPattern); return; } if (baselineEntries.count() != testEntries.count()) { SkDebugf("Baseline and test patterns do not yield corresponding number of files\n"); return; } for (int entryIndex = 0; entryIndex < baselineEntries.count(); entryIndex++) { const char* baselineFilename = baselineEntries[entryIndex].c_str(); const char* testFilename = testEntries [entryIndex].c_str(); this->addDiff(baselineFilename, testFilename); } }
int handle(Request* request, MHD_Connection* connection, const char* url, const char* method, const char* upload_data, size_t* upload_data_size) override { SkTArray<SkString> commands; SkStrSplit(url, "/", &commands); if (!request->fPicture.get() || commands.count() > 3) { return MHD_NO; } // /cmd or /cmd/N or /cmd/N/[0|1] if (commands.count() == 1 && 0 == strcmp(method, MHD_HTTP_METHOD_GET)) { int n = request->fDebugCanvas->getSize() - 1; return SendJSON(connection, request->fDebugCanvas, n); } // /cmd/N, for now only delete supported if (commands.count() == 2 && 0 == strcmp(method, MHD_HTTP_METHOD_DELETE)) { int n; sscanf(commands[1].c_str(), "%d", &n); request->fDebugCanvas->deleteDrawCommandAt(n); return MHD_YES; } // /cmd/N/[0|1] if (commands.count() == 3 && 0 == strcmp(method, MHD_HTTP_METHOD_POST)) { int n, toggle; sscanf(commands[1].c_str(), "%d", &n); sscanf(commands[2].c_str(), "%d", &toggle); request->fDebugCanvas->toggleCommand(n, toggle); return MHD_YES; } return MHD_NO; }
int FindOrAdd(IDWriteFontFileLoader* fontFileLoader, const void* refKey, UINT32 refKeySize) const { SkTScopedComPtr<IUnknown> fontFileLoaderId; HR_GENERAL(fontFileLoader->QueryInterface(&fontFileLoaderId), "Failed to re-convert to IDWriteFontFileLoader.", SkFontIdentity::kInvalidDataId); SkAutoMutexAcquire ama(fDataIdCacheMutex); int count = fDataIdCache.count(); int i; for (i = 0; i < count; ++i) { const DataId& current = fDataIdCache[i]; if (fontFileLoaderId.get() == current.fLoader && refKeySize == current.fKeySize && 0 == memcmp(refKey, current.fKey, refKeySize)) { return i; } } DataId& added = fDataIdCache.push_back(); added.fLoader = fontFileLoaderId.release(); // Ref is passed. added.fKey = sk_malloc_throw(refKeySize); memcpy(added.fKey, refKey, refKeySize); added.fKeySize = refKeySize; return i; }
void buildNameToFamilyMap(SkTDArray<FontFamily*> families, const bool isolated) { for (int i = 0; i < families.count(); i++) { FontFamily& family = *families[i]; SkTArray<NameToFamily, true>* nameToFamily = &fNameToFamilyMap; if (family.fIsFallbackFont) { nameToFamily = &fFallbackNameToFamilyMap; if (0 == family.fNames.count()) { SkString& fallbackName = family.fNames.push_back(); fallbackName.printf("%.2x##fallback", i); } } sk_sp<SkFontStyleSet_Android> newSet = sk_make_sp<SkFontStyleSet_Android>(family, fScanner, isolated); if (0 == newSet->count()) { continue; } for (const SkString& name : family.fNames) { nameToFamily->emplace_back(NameToFamily{name, newSet.get()}); } fStyleSets.emplace_back(std::move(newSet)); } }
void GrVkPipelineState::writeSamplers(GrVkGpu* gpu, const SkTArray<const GrTextureAccess*>& textureBindings, bool allowSRGBInputs) { SkASSERT(fNumSamplers == textureBindings.count()); for (int i = 0; i < textureBindings.count(); ++i) { const GrTextureParams& params = textureBindings[i]->getParams(); GrVkTexture* texture = static_cast<GrVkTexture*>(textureBindings[i]->getTexture()); if (GrTextureParams::kMipMap_FilterMode == params.filterMode()) { if (texture->texturePriv().mipMapsAreDirty()) { gpu->generateMipmap(texture); texture->texturePriv().dirtyMipMaps(false); } } fSamplers.push(gpu->resourceProvider().findOrCreateCompatibleSampler(params, texture->texturePriv().maxMipMapLevel())); const GrVkResource* textureResource = texture->resource(); textureResource->ref(); fTextures.push(textureResource); const GrVkImageView* textureView = texture->textureView(allowSRGBInputs); textureView->ref(); fTextureViews.push(textureView); // Change texture layout so it can be read in shader texture->setImageLayout(gpu, VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL, VK_ACCESS_SHADER_READ_BIT, VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT, false); VkDescriptorImageInfo imageInfo; memset(&imageInfo, 0, sizeof(VkDescriptorImageInfo)); imageInfo.sampler = fSamplers[i]->sampler(); imageInfo.imageView = textureView->imageView(); imageInfo.imageLayout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL; VkWriteDescriptorSet writeInfo; memset(&writeInfo, 0, sizeof(VkWriteDescriptorSet)); writeInfo.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET; writeInfo.pNext = nullptr; writeInfo.dstSet = fDescriptorSets[GrVkUniformHandler::kSamplerDescSet]; writeInfo.dstBinding = i; writeInfo.dstArrayElement = 0; writeInfo.descriptorCount = 1; writeInfo.descriptorType = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER; writeInfo.pImageInfo = &imageInfo; writeInfo.pBufferInfo = nullptr; writeInfo.pTexelBufferView = nullptr; GR_VK_CALL(gpu->vkInterface(), UpdateDescriptorSets(gpu->device(), 1, &writeInfo, 0, nullptr)); } }
void SkResourceCache::checkMessages() { SkTArray<PurgeSharedIDMessage> msgs; fPurgeSharedIDInbox.poll(&msgs); for (int i = 0; i < msgs.count(); ++i) { this->purgeSharedID(msgs[i].fSharedID); } }
int tool_main(int argc, char** argv) { SetupCrashHandler(); SkAutoGraphics ag; SkCommandLineFlags::Parse(argc, argv); if (FLAGS_dryRun) { FLAGS_verbose = true; } #if SK_ENABLE_INST_COUNT gPrintInstCount = FLAGS_leaks; #endif SkTArray<SkString> configs; for (int i = 0; i < FLAGS_config.count(); i++) { SkStrSplit(FLAGS_config[i], ", ", &configs); } SkTDArray<GMRegistry::Factory> gms; SkAutoTDelete<DM::Expectations> expectations(SkNEW(DM::NoExpectations)); if (FLAGS_gms) { append_matching_factories<GM>(GMRegistry::Head(), &gms); if (FLAGS_expectations.count() > 0) { const char* path = FLAGS_expectations[0]; if (sk_isdir(path)) { expectations.reset(SkNEW_ARGS(DM::WriteTask::Expectations, (path))); } else { expectations.reset(SkNEW_ARGS(DM::JsonExpectations, (path))); } } } SkTDArray<BenchRegistry::Factory> benches; if (FLAGS_benches) { append_matching_factories<Benchmark>(BenchRegistry::Head(), &benches); } SkTDArray<TestRegistry::Factory> tests; if (FLAGS_tests) { append_matching_factories<Test>(TestRegistry::Head(), &tests); } SkDebugf("(%d GMs, %d benches) x %d configs, %d tests\n", gms.count(), benches.count(), configs.count(), tests.count()); DM::Reporter reporter; DM::TaskRunner tasks(FLAGS_threads, FLAGS_gpuThreads); kick_off_gms(gms, configs, *expectations, &reporter, &tasks); kick_off_benches(benches, configs, &reporter, &tasks); kick_off_tests(tests, &reporter, &tasks); kick_off_skps(&reporter, &tasks); tasks.wait(); SkDebugf("\n"); SkTArray<SkString> failures; reporter.getFailures(&failures); report_failures(failures); return failures.count() > 0; }
void JsonWriter::DumpJson() { if (FLAGS_writePath.isEmpty()) { return; } Json::Value root; for (int i = 1; i < FLAGS_properties.count(); i += 2) { root[FLAGS_properties[i-1]] = FLAGS_properties[i]; } for (int i = 1; i < FLAGS_key.count(); i += 2) { root["key"][FLAGS_key[i-1]] = FLAGS_key[i]; } { SkAutoMutexAcquire lock(&gBitmapResultLock); for (int i = 0; i < gBitmapResults.count(); i++) { Json::Value result; result["key"]["name"] = gBitmapResults[i].name.c_str(); result["key"]["config"] = gBitmapResults[i].config.c_str(); result["key"]["source_type"] = gBitmapResults[i].sourceType.c_str(); result["options"]["ext"] = gBitmapResults[i].ext.c_str(); result["options"]["gamma_correct"] = gBitmapResults[i].gammaCorrect ? "yes" : "no"; result["md5"] = gBitmapResults[i].md5.c_str(); // Source options only need to be part of the key if they exist. // Source type by source type, we either always set options or never set options. if (!gBitmapResults[i].sourceOptions.isEmpty()) { result["key"]["source_options"] = gBitmapResults[i].sourceOptions.c_str(); } root["results"].append(result); } } { SkAutoMutexAcquire lock(gFailureLock); for (int i = 0; i < gFailures.count(); i++) { Json::Value result; result["file_name"] = gFailures[i].fileName; result["line_no"] = gFailures[i].lineNo; result["condition"] = gFailures[i].condition; result["message"] = gFailures[i].message.c_str(); root["test_results"]["failures"].append(result); } } int maxResidentSetSizeMB = sk_tools::getMaxResidentSetSizeMB(); if (maxResidentSetSizeMB != -1) { root["max_rss_MB"] = sk_tools::getMaxResidentSetSizeMB(); } SkString path = SkOSPath::Join(FLAGS_writePath[0], "dm.json"); sk_mkdir(FLAGS_writePath[0]); SkFILEWStream stream(path.c_str()); stream.writeText(Json::StyledWriter().write(root).c_str()); stream.flush(); }
void SkInternalAtlasTextTarget::deleteOps() { for (int i = 0; i < fOps.count(); ++i) { if (fOps[i]) { fOpMemoryPool->release(std::move(fOps[i])); } } fOps.reset(); }
// return root node. static sk_sp<SkPDFDict> generate_page_tree(SkTArray<sk_sp<SkPDFDict>>* pages) { // PDF wants a tree describing all the pages in the document. We arbitrary // choose 8 (kNodeSize) as the number of allowed children. The internal // nodes have type "Pages" with an array of children, a parent pointer, and // the number of leaves below the node as "Count." The leaves are passed // into the method, have type "Page" and need a parent pointer. This method // builds the tree bottom up, skipping internal nodes that would have only // one child. static const int kNodeSize = 8; // curNodes takes a reference to its items, which it passes to pageTree. int totalPageCount = pages->count(); SkTArray<sk_sp<SkPDFDict>> curNodes; curNodes.swap(pages); // nextRoundNodes passes its references to nodes on to curNodes. int treeCapacity = kNodeSize; do { SkTArray<sk_sp<SkPDFDict>> nextRoundNodes; for (int i = 0; i < curNodes.count(); ) { if (i > 0 && i + 1 == curNodes.count()) { SkASSERT(curNodes[i]); nextRoundNodes.emplace_back(std::move(curNodes[i])); break; } auto newNode = sk_make_sp<SkPDFDict>("Pages"); auto kids = sk_make_sp<SkPDFArray>(); kids->reserve(kNodeSize); int count = 0; for (; i < curNodes.count() && count < kNodeSize; i++, count++) { SkASSERT(curNodes[i]); curNodes[i]->insertObjRef("Parent", newNode); kids->appendObjRef(std::move(curNodes[i])); } // treeCapacity is the number of leaf nodes possible for the // current set of subtrees being generated. (i.e. 8, 64, 512, ...). // It is hard to count the number of leaf nodes in the current // subtree. However, by construction, we know that unless it's the // last subtree for the current depth, the leaf count will be // treeCapacity, otherwise it's what ever is left over after // consuming treeCapacity chunks. int pageCount = treeCapacity; if (i == curNodes.count()) { pageCount = ((totalPageCount - 1) % treeCapacity) + 1; } newNode->insertInt("Count", pageCount); newNode->insertObject("Kids", std::move(kids)); nextRoundNodes.emplace_back(std::move(newNode)); } SkDEBUGCODE( for (const auto& n : curNodes) { SkASSERT(!n); } ); curNodes.swap(&nextRoundNodes); nextRoundNodes.reset(); treeCapacity *= kNodeSize; } while (curNodes.count() > 1);
// TODO(chudy): Free command string memory. SkTArray<SkString>* SkDebugCanvas::getDrawCommandsAsStrings() const { SkTArray<SkString>* commandString = new SkTArray<SkString>(fCommandVector.count()); if (!fCommandVector.isEmpty()) { for (int i = 0; i < fCommandVector.count(); i ++) { commandString->push_back() = fCommandVector[i]->toString(); } } return commandString; }
void GrVkProgram::writeSamplers(const GrVkGpu* gpu, const SkTArray<const GrTextureAccess*>& textureBindings) { SkASSERT(fNumSamplers == textureBindings.count()); for (int i = 0; i < textureBindings.count(); ++i) { fSamplers.push(GrVkSampler::Create(gpu, *textureBindings[i])); GrVkTexture* texture = static_cast<GrVkTexture*>(textureBindings[i]->getTexture()); const GrVkImage::Resource* textureResource = texture->resource(); textureResource->ref(); fTextures.push(textureResource); const GrVkImageView* textureView = texture->textureView(); textureView->ref(); fTextureViews.push(textureView); // Change texture layout so it can be read in shader VkImageLayout layout = texture->currentLayout(); VkPipelineStageFlags srcStageMask = GrVkMemory::LayoutToPipelineStageFlags(layout); VkPipelineStageFlags dstStageMask = VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT; VkAccessFlags srcAccessMask = GrVkMemory::LayoutToSrcAccessMask(layout); VkAccessFlags dstAccessMask = VK_ACCESS_SHADER_READ_BIT; texture->setImageLayout(gpu, VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL, srcAccessMask, dstAccessMask, srcStageMask, dstStageMask, false); VkDescriptorImageInfo imageInfo; memset(&imageInfo, 0, sizeof(VkDescriptorImageInfo)); imageInfo.sampler = fSamplers[i]->sampler(); imageInfo.imageView = texture->textureView()->imageView(); imageInfo.imageLayout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL; VkWriteDescriptorSet writeInfo; memset(&writeInfo, 0, sizeof(VkWriteDescriptorSet)); writeInfo.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET; writeInfo.pNext = nullptr; writeInfo.dstSet = fDescriptorSets[GrVkUniformHandler::kSamplerDescSet]; writeInfo.dstBinding = i; writeInfo.dstArrayElement = 0; writeInfo.descriptorCount = 1; writeInfo.descriptorType = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER; writeInfo.pImageInfo = &imageInfo; writeInfo.pBufferInfo = nullptr; writeInfo.pTexelBufferView = nullptr; GR_VK_CALL(gpu->vkInterface(), UpdateDescriptorSets(gpu->device(), 1, &writeInfo, 0, nullptr)); } }
SkCommandLineConfigGpu* parse_command_line_config_gpu(const SkString& tag, const SkTArray<SkString>& vias, const SkString& options) { // Defaults for GPU backend. bool seenAPI = false; SkCommandLineConfigGpu::ContextType contextType = GrContextFactory::kNativeGL_ContextType; bool seenUseNVPR = false; bool useNVPR = false; bool seenUseInstanced = false; bool useInstanced = false; bool seenUseDIText =false; bool useDIText = false; bool seenSamples = false; int samples = 0; bool seenColor = false; SkColorType colorType = kN32_SkColorType; sk_sp<SkColorSpace> colorSpace = nullptr; SkTArray<SkString> optionParts; SkStrSplit(options.c_str(), ",", kStrict_SkStrSplitMode, &optionParts); for (int i = 0; i < optionParts.count(); ++i) { SkTArray<SkString> keyValueParts; SkStrSplit(optionParts[i].c_str(), "=", kStrict_SkStrSplitMode, &keyValueParts); if (keyValueParts.count() != 2) { return nullptr; } const SkString& key = keyValueParts[0]; const SkString& value = keyValueParts[1]; bool valueOk = false; if (key.equals("api") && !seenAPI) { valueOk = parse_option_gpu_api(value, &contextType); seenAPI = true; } else if (key.equals("nvpr") && !seenUseNVPR) { valueOk = parse_option_bool(value, &useNVPR); seenUseNVPR = true; } else if (key.equals("inst") && !seenUseInstanced) { valueOk = parse_option_bool(value, &useInstanced); seenUseInstanced = true; } else if (key.equals("dit") && !seenUseDIText) { valueOk = parse_option_bool(value, &useDIText); seenUseDIText = true; } else if (key.equals("samples") && !seenSamples) { valueOk = parse_option_int(value, &samples); seenSamples = true; } else if (key.equals("color") && !seenColor) { valueOk = parse_option_gpu_color(value, &colorType, &colorSpace); seenColor = true; } if (!valueOk) { return nullptr; } } return new SkCommandLineConfigGpu(tag, vias, contextType, useNVPR, useInstanced, useDIText, samples, colorType, colorSpace); }
// Splits off the last N suffixes of name (splitting on _) and appends them to out. // Returns the total number of characters consumed. static int split_suffixes(int N, const char* name, SkTArray<SkString>* out) { SkTArray<SkString> split; SkStrSplit(name, "_", &split); int consumed = 0; for (int i = 0; i < N; i++) { // We're splitting off suffixes from the back to front. out->push_back(split[split.count()-i-1]); consumed += out->back().size() + 1; // Add one for the _. } return consumed; }
// Prints shaders one line at the time. This ensures they don't get truncated by the adb log. void PrintLineByLine(const char* header, const SkSL::String& text) { if (header) { SkDebugf("%s\n", header); } SkSL::String pretty = PrettyPrint(text); SkTArray<SkString> lines; SkStrSplit(pretty.c_str(), "\n", kStrict_SkStrSplitMode, &lines); for (int i = 0; i < lines.count(); ++i) { SkDebugf("%4i\t%s\n", i + 1, lines[i].c_str()); } }
static void report_failures(const SkTArray<SkString>& failures) { if (failures.count() == 0) { return; } SkDebugf("Failures:\n"); for (int i = 0; i < failures.count(); i++) { SkDebugf(" %s\n", failures[i].c_str()); } SkDebugf("%d failures.\n", failures.count()); }
static int find_or_append(SkTArray<sk_sp<T>>& array, T* obj) { for (int i = 0; i < array.count(); i++) { if (equals(array[i].get(), obj)) { return i; } } array.push_back(sk_ref_sp(obj)); return array.count() - 1; }
// finds the index of ext in strings or a negative result if ext is not found. static int find_string(const SkTArray<SkString>& strings, const char ext[]) { if (strings.empty()) { return -1; } SkString extensionStr(ext); int idx = SkTSearch<SkString, extension_compare>(&strings.front(), strings.count(), extensionStr, sizeof(SkString)); return idx; }
void GLCpuPosInstancedArraysBench::teardown(const GrGLInterface* gl) { GR_GL_CALL(gl, BindBuffer(GR_GL_ARRAY_BUFFER, 0)); GR_GL_CALL(gl, BindVertexArray(0)); GR_GL_CALL(gl, BindTexture(GR_GL_TEXTURE_2D, 0)); GR_GL_CALL(gl, BindFramebuffer(GR_GL_FRAMEBUFFER, 0)); GR_GL_CALL(gl, DeleteTextures(1, &fTexture)); GR_GL_CALL(gl, DeleteProgram(fProgram)); GR_GL_CALL(gl, DeleteBuffers(fBuffers.count(), fBuffers.begin())); GR_GL_CALL(gl, DeleteVertexArrays(1, &fVAO)); fBuffers.reset(); }
/** * Helper function to write a bitmap subset to a file. Only called if subsets were created * and a writePath was provided. Behaves differently depending on * FLAGS_writeChecksumBasedFilenames. If true: * Writes the image to a PNG file named according to the digest hash, as described in * write_bitmap. * If false: * Creates a subdirectory called 'subsets' and writes a PNG to that directory. Also * creates a subdirectory called 'extracted' and writes a bitmap created using * extractSubset to a PNG in that directory. Both files will represent the same * subrectangle and have the same name for convenient comparison. In this case, the * digest is ignored. * * @param writePath Parent directory to hold the folders for the PNG files to write. Must * not be NULL. * @param subsetName Basename of the original file, with the dimensions of the subset tacked * on. Used to name the new file/folder. * @param bitmapAndDigestFromDecodeSubset SkBitmap (with digest) created by * SkImageDecoder::DecodeSubset, using rect as the area to decode. * @param rect Rectangle of the area decoded into bitmapFromDecodeSubset. Used to call * extractSubset on originalBitmap to create a bitmap with the same dimensions/pixels as * bitmapFromDecodeSubset (assuming decodeSubset worked properly). * @param originalBitmap SkBitmap decoded from the same stream as bitmapFromDecodeSubset, * using SkImageDecoder::decode to get the entire image. Used to create a PNG file for * comparison to the PNG created by bitmapAndDigestFromDecodeSubset's bitmap. * @return bool Whether the function succeeded at drawing the decoded subset and the extracted * subset to files. */ static bool write_subset(const char* writePath, const SkString& subsetName, const skiagm::BitmapAndDigest bitmapAndDigestFromDecodeSubset, SkIRect rect, const SkBitmap& originalBitmap) { // All parameters must be valid. SkASSERT(writePath != NULL); SkString subsetPath; if (FLAGS_writeChecksumBasedFilenames) { subsetPath.set(writePath); } else { // Create a subdirectory to hold the results of decodeSubset. subsetPath = SkOSPath::SkPathJoin(writePath, "subsets"); if (!sk_mkdir(subsetPath.c_str())) { gFailedSubsetDecodes.push_back().printf("Successfully decoded subset %s, but " "failed to create a directory to write to.", subsetName.c_str()); return false; } } SkAssertResult(write_bitmap(subsetPath.c_str(), subsetName.c_str(), bitmapAndDigestFromDecodeSubset)); gSuccessfulSubsetDecodes.push_back().printf("\twrote %s", subsetName.c_str()); if (!FLAGS_writeChecksumBasedFilenames) { // FIXME: The goal of extracting the subset is for visual comparison/using skdiff/skpdiff. // Currently disabling for writeChecksumBasedFilenames since it will be trickier to // determine which files to compare. // Also use extractSubset from the original for visual comparison. // Write the result to a file in a separate subdirectory. SkBitmap extractedSubset; if (!originalBitmap.extractSubset(&extractedSubset, rect)) { gFailedSubsetDecodes.push_back().printf("Successfully decoded subset %s, but failed " "to extract a similar subset for comparison.", subsetName.c_str()); return false; } SkString dirExtracted = SkOSPath::SkPathJoin(writePath, "extracted"); if (!sk_mkdir(dirExtracted.c_str())) { gFailedSubsetDecodes.push_back().printf("Successfully decoded subset%s, but failed " "to create a directory for extractSubset " "comparison.", subsetName.c_str()); return false; } skiagm::BitmapAndDigest bitmapAndDigestFromExtractSubset(extractedSubset); SkAssertResult(write_bitmap(dirExtracted.c_str(), subsetName.c_str(), bitmapAndDigestFromExtractSubset)); } return true; }
static void print_status() { int curr = sk_tools::getCurrResidentSetSizeMB(), peak = sk_tools::getMaxResidentSetSizeMB(); SkString elapsed = HumanizeMs(SkTime::GetMSecs() - kStartMs); SkAutoMutexAcquire lock(gMutex); info("\n%s elapsed, %d active, %d queued, %dMB RAM, %dMB peak\n", elapsed.c_str(), gRunning.count(), gPending - gRunning.count(), curr, peak); for (auto& task : gRunning) { info("\t%s\n", task.c_str()); } }
int main(int argc, char* const argv[]) { SkTArray<SkString> inputs; sk_tools::PictureBenchmark* benchmark = NULL; parse_commandline(argc, argv, &inputs, benchmark); for (int i = 0; i < inputs.count(); ++i) { process_input(inputs[i], *benchmark); } SkDELETE(benchmark); }
void MakeContourList(SkTArray<SkOpContour>& contours, SkTArray<SkOpContour*, true>& list, bool evenOdd, bool oppEvenOdd) { int count = contours.count(); if (count == 0) { return; } for (int index = 0; index < count; ++index) { SkOpContour& contour = contours[index]; contour.setOppXor(contour.operand() ? evenOdd : oppEvenOdd); list.push_back(&contour); } SkTQSort<SkOpContour>(list.begin(), list.end() - 1); }
static void report_failures(const DM::Reporter& reporter) { SkTArray<SkString> failures; reporter.getFailures(&failures); if (failures.count() == 0) { return; } SkDebugf("Failures:\n"); for (int i = 0; i < failures.count(); i++) { SkDebugf(" %s\n", failures[i].c_str()); } }
GrPathRange* GrGLPathRendering::createGlyphs(const SkTypeface* typeface, const SkDescriptor* desc, const SkStrokeRec& stroke) { if (NULL != desc || !caps().glyphLoadingSupport) { return GrPathRendering::createGlyphs(typeface, desc, stroke); } if (NULL == typeface) { typeface = SkTypeface::GetDefaultTypeface(); SkASSERT(NULL != typeface); } int faceIndex; SkAutoTDelete<SkStream> fontStream(typeface->openStream(&faceIndex)); const size_t fontDataLength = fontStream->getLength(); if (0 == fontDataLength) { return GrPathRendering::createGlyphs(typeface, NULL, stroke); } SkTArray<uint8_t> fontTempBuffer; const void* fontData = fontStream->getMemoryBase(); if (NULL == fontData) { // TODO: Find a more efficient way to pass the font data (e.g. open file descriptor). fontTempBuffer.reset(SkToInt(fontDataLength)); fontStream->read(&fontTempBuffer.front(), fontDataLength); fontData = &fontTempBuffer.front(); } const int numPaths = typeface->countGlyphs(); const GrGLuint basePathID = this->genPaths(numPaths); SkAutoTUnref<GrGLPath> templatePath(SkNEW_ARGS(GrGLPath, (fGpu, SkPath(), stroke))); GrGLenum status; GL_CALL_RET(status, PathMemoryGlyphIndexArray(basePathID, GR_GL_STANDARD_FONT_FORMAT, fontDataLength, fontData, faceIndex, 0, numPaths, templatePath->pathID(), SkPaint::kCanonicalTextSizeForPaths)); if (GR_GL_FONT_GLYPHS_AVAILABLE != status) { this->deletePaths(basePathID, numPaths); return GrPathRendering::createGlyphs(typeface, NULL, stroke); } // This is a crude approximation. We may want to consider giving this class // a pseudo PathGenerator whose sole purpose is to track the approximate gpu // memory size. const size_t gpuMemorySize = fontDataLength / 4; return SkNEW_ARGS(GrGLPathRange, (fGpu, basePathID, numPaths, gpuMemorySize, stroke)); }
DEF_TEST(GrAllocator, reporter) { // Test combinations of allocators with and without stack storage and with different block // sizes. SkTArray<GrTAllocator<C>*> allocators; GrTAllocator<C> a1(1); allocators.push_back(&a1); GrTAllocator<C> a2(2); allocators.push_back(&a2); GrTAllocator<C> a5(5); allocators.push_back(&a5); GrSTAllocator<1, C> sa1; allocators.push_back(&a1); GrSTAllocator<3, C> sa3; allocators.push_back(&sa3); GrSTAllocator<4, C> sa4; allocators.push_back(&sa4); for (int i = 0; i < allocators.count(); ++i) { check_allocator(allocators[i], 0, 0, reporter); check_allocator(allocators[i], 1, 1, reporter); check_allocator(allocators[i], 2, 2, reporter); check_allocator(allocators[i], 10, 1, reporter); check_allocator(allocators[i], 10, 5, reporter); check_allocator(allocators[i], 10, 10, reporter); check_allocator(allocators[i], 100, 10, reporter); } }
void SkConvolutionFilter1D::AddFilter(int filterOffset, const float* filterValues, int filterLength) { SkASSERT(filterLength > 0); SkTArray<ConvolutionFixed> fixedValues; fixedValues.reset(filterLength); for (int i = 0; i < filterLength; ++i) { fixedValues.push_back(FloatToFixed(filterValues[i])); } AddFilter(filterOffset, &fixedValues[0], filterLength); }
void SkOpContour::debugShowWindingValues(const SkTArray<SkOpContour*, true>& contourList) { // int ofInterest = 1 << 1 | 1 << 5 | 1 << 9 | 1 << 13; // int ofInterest = 1 << 4 | 1 << 8 | 1 << 12 | 1 << 16; int ofInterest = 1 << 5 | 1 << 8; int total = 0; int index; for (index = 0; index < contourList.count(); ++index) { total += contourList[index]->segments().count(); } int sum = 0; for (index = 0; index < contourList.count(); ++index) { sum += contourList[index]->debugShowWindingValues(total, ofInterest); } // SkDebugf("%s total=%d\n", __FUNCTION__, sum); }
void GLCpuPosInstancedArraysBench::setupSingleVbo(const GrGLInterface* gl, const SkMatrix* viewMatrices) { // Constants for our various shader programs Vertex vertices[kVerticesPerTri * kNumTri]; for (uint32_t i = 0; i < kNumTri; i++) { Vertex* v = &vertices[i * kVerticesPerTri]; v[0].fPositions.set(-1.0f, -1.0f); v[1].fPositions.set( 1.0f, -1.0f); v[2].fPositions.set( 1.0f, 1.0f); SkPoint* position = reinterpret_cast<SkPoint*>(v); viewMatrices[i].mapPointsWithStride(position, sizeof(Vertex), kVerticesPerTri); // set colors float color = i == kNumTri - 1 ? 1.0f : 0.0f; for (uint32_t j = 0; j < kVerticesPerTri; j++) { uint32_t offset = 0; v->fColors[offset++] = color; v->fColors[offset++] = 0.0f; v->fColors[offset++] = 0.0f; v++; } } GrGLuint vbo; // setup VBO GR_GL_CALL(gl, GenBuffers(1, &vbo)); GR_GL_CALL(gl, BindBuffer(GR_GL_ARRAY_BUFFER, vbo)); GR_GL_CALL(gl, EnableVertexAttribArray(0)); GR_GL_CALL(gl, EnableVertexAttribArray(1)); GR_GL_CALL(gl, VertexAttribPointer(0, 2, GR_GL_FLOAT, GR_GL_FALSE, sizeof(Vertex), (GrGLvoid*)0)); GR_GL_CALL(gl, VertexAttribPointer(1, 3, GR_GL_FLOAT, GR_GL_FALSE, sizeof(Vertex), (GrGLvoid*)(sizeof(SkPoint)))); GR_GL_CALL(gl, BufferData(GR_GL_ARRAY_BUFFER, sizeof(vertices), vertices, GR_GL_STATIC_DRAW)); fBuffers.push_back(vbo); }