コード例 #1
0
ファイル: PictureRenderer.cpp プロジェクト: UIKit0/skia
bool TiledPictureRenderer::render(const SkString* path, SkBitmap** out) {
    SkASSERT(fPicture != NULL);
    if (NULL == fPicture) {
        return false;
    }

    SkBitmap bitmap;
    if (out){
        *out = SkNEW(SkBitmap);
        setup_bitmap(*out, fPicture->width(), fPicture->height());
        setup_bitmap(&bitmap, fTileWidth, fTileHeight);
    }
    bool success = true;
    for (int i = 0; i < fTileRects.count(); ++i) {
        draw_tile_to_canvas(fCanvas, fTileRects[i], fPicture);
        if (NULL != path) {
            success &= writeAppendNumber(fCanvas, path, i, fJsonSummaryPtr);
        }
        if (NULL != out) {
            if (fCanvas->readPixels(&bitmap, 0, 0)) {
                // Add this tile to the entire bitmap.
                bitmapCopyAtOffset(bitmap, *out, SkScalarFloorToInt(fTileRects[i].left()),
                                   SkScalarFloorToInt(fTileRects[i].top()));
            } else {
                success = false;
            }
        }
    }
    return success;
}
コード例 #2
0
ファイル: PictureRenderer.cpp プロジェクト: miaoshunping/skia
bool TiledPictureRenderer::render(SkBitmap** out) {
    SkASSERT(fPicture != NULL);
    if (NULL == fPicture) {
        return false;
    }

    SkBitmap bitmap;
    if (out){
        *out = SkNEW(SkBitmap);
        setup_bitmap(*out, fPicture->width(), fPicture->height());
        setup_bitmap(&bitmap, fTileWidth, fTileHeight);
    }
    bool success = true;
    for (int i = 0; i < fTileRects.count(); ++i) {
        draw_tile_to_canvas(fCanvas, fTileRects[i], fPicture);
        if (fEnableWrites) {
            success &= write(fCanvas, fWritePath, fMismatchPath, fInputFilename, fJsonSummaryPtr,
                             fUseChecksumBasedFilenames, &i);
        }
        if (NULL != out) {
            if (fCanvas->readPixels(&bitmap, 0, 0)) {
                // Add this tile to the entire bitmap.
                bitmapCopyAtOffset(bitmap, *out, SkScalarFloorToInt(fTileRects[i].left()),
                                   SkScalarFloorToInt(fTileRects[i].top()));
            } else {
                success = false;
            }
        }
    }
    return success;
}
コード例 #3
0
static bool write_bitmap(const char outName[], const SkBitmap& bm) {
    SkISize size = opaqueSize(bm);
    SkBitmap dst;
    setup_bitmap(&dst, size.width(), size.height());

    for (int y = 0 ; y < dst.height(); y++) {
        for (int x = 0 ; x < dst.width(); x++) {
            SkColor color = bm.getColor(x, y);
            if (SkColorGetA(color) != 0xff) {
                int a = SkColorGetA(color);
                int r = SkColorGetR(color);
                int g = SkColorGetG(color);
                int b = SkColorGetB(color);
                if (a == 0) {
                    r = g = b = 0;
                } else {
                    r = (r * a) / 255;
                    g = (g * a) / 255;
                    b = (b * a) / 255;
                    a = 255;
                }
                color = SkColorSetARGB((U8CPU)a, (U8CPU)r, (U8CPU)g, (U8CPU)b);
            }
            *dst.getAddr32(x, y) = color;
        }
    }

    return SkImageEncoder::EncodeFile(outName, dst, SkImageEncoder::kPNG_Type, 100);
}
コード例 #4
0
bool SimplePictureRenderer::render(SkBitmap** out) {
    SkASSERT(fCanvas.get() != NULL);
    SkASSERT(fPicture);
    if (NULL == fCanvas.get() || NULL == fPicture) {
        return false;
    }

    if (fUseMultiPictureDraw) {
        SkMultiPictureDraw mpd;

        mpd.add(fCanvas, fPicture);

        mpd.draw();
    } else {
        fCanvas->drawPicture(fPicture);
    }
    fCanvas->flush();
    if (out) {
        *out = SkNEW(SkBitmap);
        setup_bitmap(*out, SkScalarCeilToInt(fPicture->cullRect().width()),
                           SkScalarCeilToInt(fPicture->cullRect().height()));
        fCanvas->readPixels(*out, 0, 0);
    }
    if (fEnableWrites) {
        return write(fCanvas, fWritePath, fMismatchPath, fInputFilename, fJsonSummaryPtr,
                     fUseChecksumBasedFilenames);
    } else {
        return true;
    }
}
コード例 #5
0
bool PipePictureRenderer::render(SkBitmap** out) {
    SkASSERT(fCanvas.get() != NULL);
    SkASSERT(fPicture != NULL);
    if (NULL == fCanvas.get() || NULL == fPicture) {
        return false;
    }

    PipeController pipeController(fCanvas.get());
    SkGPipeWriter writer;
    SkCanvas* pipeCanvas = writer.startRecording(&pipeController);
    pipeCanvas->drawPicture(fPicture);
    writer.endRecording();
    fCanvas->flush();
    if (out) {
        *out = SkNEW(SkBitmap);
        setup_bitmap(*out, SkScalarCeilToInt(fPicture->cullRect().width()),
                           SkScalarCeilToInt(fPicture->cullRect().height()));
        fCanvas->readPixels(*out, 0, 0);
    }
    if (fEnableWrites) {
        return write(fCanvas, fWritePath, fMismatchPath, fInputFilename, fJsonSummaryPtr,
                     fUseChecksumBasedFilenames);
    } else {
        return true;
    }
}
コード例 #6
0
ファイル: kmain.c プロジェクト: Detegr/tapiOS
void kmain(struct multiboot* b, uint32_t magic)
{
	hide_cursor();
	cls();
	setup_gdt();
	setup_idt();
	if(b->mods_count == 1)
	{
		uint32_t mods_start_addr=*(uint32_t*)(b->mods_addr);
		uint32_t mods_end_addr=*(uint32_t*)(b->mods_addr + 4);
		if(((uint32_t)&__kernel_end - KERNEL_VMA) < mods_end_addr) kernel_end_addr=(mods_end_addr & 0xFFFFF000) + 0x1000;
	}
	setup_bitmap();
	setup_vmm();
	setup_pic();
	setup_tasking();
	setup_process_tree();
	set_timer_freq(100);

	pci_init();
	setup_network();

	b=(struct multiboot*)((uint8_t*)b+KERNEL_VMA);
	uint32_t mods_addr=*(uint32_t*)(b->mods_addr + KERNEL_VMA) + KERNEL_VMA;
	root_fs=ext2_fs_init((uint8_t*)mods_addr);
	struct inode *devfs=devfs_init();
	struct inode *devfs_root=vfs_search((struct inode*)root_fs, "/dev");
	if(devfs_root)
	{
		vfs_mount(devfs, devfs_root);
		register_tty_driver();
		register_kbd_driver();
		register_rtl8139_driver();
	}
	else kprintf("Could not mount /dev, no such directory\n");

	kprintf("\n%@Welcome to tapiOS!%@\n\n", 0x05, 0x07, b->mods_count, 0x03);

	struct inode *node=vfs_search((struct inode*)root_fs, "/bin/init");
	if(node)
	{
		struct file *init=vfs_open(node, NULL, O_RDONLY);
		uint8_t *init_mem=kmalloc(node->size);
		int read=vfs_read(init, init_mem, node->size);
		vaddr_t entrypoint=init_elf_get_entry_point(init_mem);
		setup_initial_process(entrypoint);
	}
	else kprintf("Init not found\n");
	__asm__ volatile("hltloop: hlt; jmp hltloop");

	PANIC();
}
コード例 #7
0
ファイル: PDFPrimitivesTest.cpp プロジェクト: Adenilson/skia
static void TestUncompressed(skiatest::Reporter* reporter) {
    SkBitmap bitmap;
    setup_bitmap(&bitmap, 1, 1);
    TestImage(reporter, bitmap,
              "/Subtype /Image\n"
              "/Width 1\n"
              "/Height 1\n"
              "/ColorSpace /DeviceRGB\n"
              "/BitsPerComponent 8\n"
              "/Length 3\n"
              ">> stream",
              true);
}
コード例 #8
0
ファイル: PDFPrimitivesTest.cpp プロジェクト: Adenilson/skia
static void TestDCTDecode(skiatest::Reporter* reporter) {
    SkBitmap bitmap;
    setup_bitmap(&bitmap, 32, 32);
    TestImage(reporter, bitmap,
              "/Subtype /Image\n"
              "/Width 32\n"
              "/Height 32\n"
              "/ColorSpace /DeviceRGB\n"
              "/BitsPerComponent 8\n"
              "/Filter /DCTDecode\n"
              "/ColorTransform 0\n"
              "/Length 21\n"
              ">> stream",
              true);
}
コード例 #9
0
ファイル: PDFPrimitivesTest.cpp プロジェクト: Adenilson/skia
static void TestFlateDecode(skiatest::Reporter* reporter) {
    if (!SkFlate::HaveFlate()) {
        return;
    }
    SkBitmap bitmap;
    setup_bitmap(&bitmap, 10, 10);
    TestImage(reporter, bitmap,
              "/Subtype /Image\n"
              "/Width 10\n"
              "/Height 10\n"
              "/ColorSpace /DeviceRGB\n"
              "/BitsPerComponent 8\n"
              "/Filter /FlateDecode\n"
              "/Length 13\n"
              ">> stream",
              false);
}
コード例 #10
0
ファイル: image.cpp プロジェクト: msarett/575
static void handle_proc(const DrawRec& rec, const char path[], const MatrixRec& mrec) {
    GBitmap bitmap;
    setup_bitmap(&bitmap, rec.fWidth, rec.fHeight);

    GCanvas* canvas = GCanvas::Create(bitmap);
    if (NULL == canvas) {
        fprintf(stderr, "failed to create canvas for [%d %d] %s\n",
                rec.fWidth, rec.fHeight, rec.fName);
        return;
    }

    canvas->setCTM(mrec.fMatrix(rec.fWidth, rec.fHeight));
    rec.fDraw(canvas);

    if (!bitmap.writeToFile(path)) {
        fprintf(stderr, "failed to write %s\n", path);
    }

    delete canvas;
    free(bitmap.fPixels);
}
コード例 #11
0
ファイル: PictureRenderer.cpp プロジェクト: miaoshunping/skia
bool SimplePictureRenderer::render(SkBitmap** out) {
    SkASSERT(fCanvas.get() != NULL);
    SkASSERT(NULL != fPicture);
    if (NULL == fCanvas.get() || NULL == fPicture) {
        return false;
    }

    fCanvas->drawPicture(fPicture);
    fCanvas->flush();
    if (NULL != out) {
        *out = SkNEW(SkBitmap);
        setup_bitmap(*out, fPicture->width(), fPicture->height());
        fCanvas->readPixels(*out, 0, 0);
    }
    if (fEnableWrites) {
        return write(fCanvas, fWritePath, fMismatchPath, fInputFilename, fJsonSummaryPtr,
                     fUseChecksumBasedFilenames);
    } else {
        return true;
    }
}
コード例 #12
0
ファイル: PictureRenderer.cpp プロジェクト: UIKit0/skia
bool SimplePictureRenderer::render(const SkString* path, SkBitmap** out) {
    SkASSERT(fCanvas.get() != NULL);
    SkASSERT(fPicture != NULL);
    if (NULL == fCanvas.get() || NULL == fPicture) {
        return false;
    }

    fCanvas->drawPicture(*fPicture);
    fCanvas->flush();
    if (NULL != path) {
        return write(fCanvas, path, fJsonSummaryPtr);
    }

    if (NULL != out) {
        *out = SkNEW(SkBitmap);
        setup_bitmap(*out, fPicture->width(), fPicture->height());
        fCanvas->readPixels(*out, 0, 0);
    }

    return true;
}
コード例 #13
0
ファイル: PictureRenderer.cpp プロジェクト: UIKit0/skia
bool PipePictureRenderer::render(const SkString* path, SkBitmap** out) {
    SkASSERT(fCanvas.get() != NULL);
    SkASSERT(fPicture != NULL);
    if (NULL == fCanvas.get() || NULL == fPicture) {
        return false;
    }

    PipeController pipeController(fCanvas.get());
    SkGPipeWriter writer;
    SkCanvas* pipeCanvas = writer.startRecording(&pipeController);
    pipeCanvas->drawPicture(*fPicture);
    writer.endRecording();
    fCanvas->flush();
    if (NULL != path) {
        return write(fCanvas, path, fJsonSummaryPtr);
    }
    if (NULL != out) {
        *out = SkNEW(SkBitmap);
        setup_bitmap(*out, fPicture->width(), fPicture->height());
        fCanvas->readPixels(*out, 0, 0);
    }
    return true;
}
コード例 #14
0
bool TiledPictureRenderer::render(SkBitmap** out) {
    SkASSERT(fPicture != NULL);
    if (NULL == fPicture) {
        return false;
    }

    SkBitmap bitmap;
    if (out) {
        *out = SkNEW(SkBitmap);
        setup_bitmap(*out, SkScalarCeilToInt(fPicture->cullRect().width()),
                           SkScalarCeilToInt(fPicture->cullRect().height()));
        setup_bitmap(&bitmap, fTileWidth, fTileHeight);
    }
    bool success = true;

    if (fUseMultiPictureDraw) {
        SkMultiPictureDraw mpd;
        SkTDArray<SkSurface*> surfaces;
        surfaces.setReserve(fTileRects.count());

        // Create a separate SkSurface/SkCanvas for each tile along with a
        // translated version of the skp (to mimic Chrome's behavior) and
        // feed all such pairs to the MultiPictureDraw.
        for (int i = 0; i < fTileRects.count(); ++i) {
            SkImageInfo ii = fCanvas->imageInfo().makeWH(fTileRects[i].width(),
                                                         fTileRects[i].height());
            *surfaces.append() = fCanvas->newSurface(ii);
            surfaces[i]->getCanvas()->setMatrix(fCanvas->getTotalMatrix());

            SkPictureRecorder recorder;
            SkRTreeFactory bbhFactory;

            SkCanvas* c = recorder.beginRecording(SkIntToScalar(fTileRects[i].width()),
                                                  SkIntToScalar(fTileRects[i].height()),
                                                  &bbhFactory,
                                                  SkPictureRecorder::kComputeSaveLayerInfo_RecordFlag);
            c->save();
            SkMatrix mat;
            mat.setTranslate(-SkIntToScalar(fTileRects[i].fLeft),
                             -SkIntToScalar(fTileRects[i].fTop));
            c->setMatrix(mat);
            c->drawPicture(fPicture);
            c->restore();

            SkAutoTUnref<SkPicture> xlatedPicture(recorder.endRecording());

            mpd.add(surfaces[i]->getCanvas(), xlatedPicture);
        }

        // Render all the buffered SkCanvases/SkPictures
        mpd.draw();

        // Sort out the results and cleanup the allocated surfaces
        for (int i = 0; i < fTileRects.count(); ++i) {
            success &= this->postRender(surfaces[i]->getCanvas(), fTileRects[i], &bitmap, out, i);
            surfaces[i]->unref();
        }
    } else {
        for (int i = 0; i < fTileRects.count(); ++i) {
            draw_tile_to_canvas(fCanvas, fTileRects[i], fPicture);
            success &= this->postRender(fCanvas, fTileRects[i], &bitmap, out, i);
        }
    }

    return success;
}
コード例 #15
0
/**
 * Write the canvas to an image file and/or JSON summary.
 *
 * @param canvas Must be non-null. Canvas to be written to a file.
 * @param writePath If nonempty, write the binary image to a file within this directory.
 * @param mismatchPath If nonempty, write the binary image to a file within this directory,
 *     but only if the image does not match expectations.
 * @param inputFilename If we are writing out a binary image, use this to build its filename.
 * @param jsonSummaryPtr If not null, add image results (checksum) to this summary.
 * @param useChecksumBasedFilenames If true, use checksum-based filenames when writing to disk.
 * @param tileNumberPtr If not null, which tile number this image contains.
 *
 * @return bool True if the operation completed successfully.
 */
static bool write(SkCanvas* canvas, const SkString& writePath, const SkString& mismatchPath,
                  const SkString& inputFilename, ImageResultsAndExpectations *jsonSummaryPtr,
                  bool useChecksumBasedFilenames, const int* tileNumberPtr=NULL) {
    SkASSERT(canvas != NULL);
    if (NULL == canvas) {
        return false;
    }

    SkBitmap bitmap;
    SkISize size = canvas->getDeviceSize();
    setup_bitmap(&bitmap, size.width(), size.height());

    canvas->readPixels(&bitmap, 0, 0);
    force_all_opaque(bitmap);
    BitmapAndDigest bitmapAndDigest(bitmap);

    SkString escapedInputFilename(inputFilename);
    replace_char(&escapedInputFilename, '.', '_');

    // TODO(epoger): what about including the config type within outputFilename?  That way,
    // we could combine results of different config types without conflicting filenames.
    SkString outputFilename;
    const char *outputSubdirPtr = NULL;
    if (useChecksumBasedFilenames) {
        ImageDigest *imageDigestPtr = bitmapAndDigest.getImageDigestPtr();
        outputSubdirPtr = escapedInputFilename.c_str();
        outputFilename.set(imageDigestPtr->getHashType());
        outputFilename.append("_");
        outputFilename.appendU64(imageDigestPtr->getHashValue());
    } else {
        outputFilename.set(escapedInputFilename);
        if (tileNumberPtr) {
            outputFilename.append("-tile");
            outputFilename.appendS32(*tileNumberPtr);
        }
    }
    outputFilename.append(".png");

    if (jsonSummaryPtr) {
        ImageDigest *imageDigestPtr = bitmapAndDigest.getImageDigestPtr();
        SkString outputRelativePath;
        if (outputSubdirPtr) {
            outputRelativePath.set(outputSubdirPtr);
            outputRelativePath.append("/");  // always use "/", even on Windows
            outputRelativePath.append(outputFilename);
        } else {
            outputRelativePath.set(outputFilename);
        }

        jsonSummaryPtr->add(inputFilename.c_str(), outputRelativePath.c_str(),
                            *imageDigestPtr, tileNumberPtr);
        if (!mismatchPath.isEmpty() &&
            !jsonSummaryPtr->getExpectation(inputFilename.c_str(),
                                            tileNumberPtr).matches(*imageDigestPtr)) {
            if (!write_bitmap_to_disk(bitmap, mismatchPath, outputSubdirPtr, outputFilename)) {
                return false;
            }
        }
    }

    if (writePath.isEmpty()) {
        return true;
    } else {
        return write_bitmap_to_disk(bitmap, writePath, outputSubdirPtr, outputFilename);
    }
}
コード例 #16
0
ファイル: prime_pthread.c プロジェクト: benHobbs/cs344
 /*************************************************************************************************
 ** Function:				main
 ** Description:			...
 *************************************************************************************************/
int main (int argc, char **argv) {
	int option;
	int print_flag = 0;
	int c_flag = 0;
	int m_flag = 0;
	unsigned int upper_bound = 0;
	unsigned int parallelism = 0;
	unsigned int bitmap_size;
	float preload_time;
	float runner_time;
	float count_time;
	float print_time;
	
	t_upper_bound = 0;
	t_parallelism = 0;
	verb_flag = 0;
	
	while ( ( option = getopt ( argc , argv , "c:m:qvh" ) ) != -1 ) {
		switch ( option ) {
			case 'c':
				c_flag = 1;
				parallelism = atoi(optarg); //number of proc
				t_parallelism = atoi(optarg); //number of proc
				break;
			case 'm':
				m_flag = 1;
				upper_bound = atoi(optarg); //number entered
				t_upper_bound = atoi(optarg); //number entered
				break;
			case 'q':
				print_flag = 1;
				break;
			case 'v':				
				verb_flag = 1;
				break;
			case 'h':
				fprintf ( stderr , "Usage: ./pprimes -c [ parallelism ] -m [ upper boundry ] -q [ hide primes ] -v [ verbose ]\n" );
				exit ( -1 );
				break;
		}
	}

	//if flags are not set, set values to default
	if ( c_flag != 1 ) {
		parallelism = 1;
		t_parallelism = 1;
		//parallelism = 10;
	}
	
	if ( m_flag != 1 ) {
		upper_bound = UINT_MAX;
		t_upper_bound = UINT_MAX;
	}
	
	//setup bitmap
	if ( verb_flag == 1 )
		fprintf ( stderr , "Creating Bitmap:\n\tUpper boundy: %u\n" , upper_bound );
	bitmap_size = upper_bound / BITS_PER_WORD + 1;
	bitmap = malloc( bitmap_size * sizeof ( unsigned char ) );
	setup_bitmap ( bitmap_size );			//build bitmap (take care of case 1 and 2)
	fflush(stdout);
	
	//preload primes into bitmap
	if ( verb_flag == 1 )
		fprintf ( stderr , "Preloading Bitmap:\n\tParallelism: %u thread(s)\n" , parallelism );
	preload_time = preload_bitmap ( upper_bound );
	fflush(stdout);

	//run prime calculations with n processes
	if ( verb_flag == 1 )
		fprintf ( stderr , "Locating Primes:\n\tPlease Wait...\n" );
	runner_time = runner ( parallelism , upper_bound );
	if ( verb_flag == 1 )
		fprintf ( stderr , "Primes Located:\n\tTotal Time: %.2f seconds\n" , runner_time + preload_time);
	
	//count the primes
	if ( verb_flag == 1 )
		fprintf ( stderr , "Counting Primes:\n\tPlease Wait...\n" );
	count_time = get_prime_count ( upper_bound );
	if ( verb_flag == 1 )
		fprintf ( stderr , "Total Run Time: %.2f\n" , runner_time + preload_time + count_time );
	
	if ( print_flag != 1 ) {
		if ( verb_flag == 1 ) {
			fprintf ( stderr , "Printing:\n\tI would suggest redirection to a file for output...\n" );
			sleep ( 3 );
		}
		
		print_time = print_twin_primes ( upper_bound );
		if ( verb_flag == 1 )
			fprintf ( stderr , "Printing Complete:\n\tTime: %.2f\n" , print_time);
	}
	
	if( bitmap != NULL) {
		free ( bitmap );
	}
	
	return 0;
}
コード例 #17
0
ファイル: pdf_viewer_main.cpp プロジェクト: Adenilson/skia
static bool render_page(const SkString& outputDir,
                        const SkString& inputFilename,
                        const SkPdfRenderer& renderer,
                        int page) {
    SkRect rect = renderer.MediaBox(page < 0 ? 0 :page);

    // Exercise all pdf codepaths as in normal rendering, but no actual bits are changed.
    if (!FLAGS_config.isEmpty() && strcmp(FLAGS_config[0], "nul") == 0) {
        SkBitmap bitmap;
        SkAutoTUnref<SkBaseDevice> device(SkNEW_ARGS(SkBitmapDevice, (bitmap)));
        SkNulCanvas canvas(device);
        renderer.renderPage(page < 0 ? 0 : page, &canvas, rect);
    } else {
        // 8888
        SkRect rect = renderer.MediaBox(page < 0 ? 0 :page);

        SkBitmap bitmap;
        SkScalar width = SkScalarMul(rect.width(),  SkDoubleToScalar(FLAGS_DPI / 72.0));
        SkScalar height = SkScalarMul(rect.height(),  SkDoubleToScalar(FLAGS_DPI / 72.0));

        rect = SkRect::MakeWH(width, height);

        SkColor background = FLAGS_transparentBackground ? SK_ColorTRANSPARENT : SK_ColorWHITE;

#ifdef PDF_DEBUG_3X
        setup_bitmap(&bitmap, 3 * (int)SkScalarToDouble(width), 3 * (int)SkScalarToDouble(height),
                     background);
#else
        setup_bitmap(&bitmap, (int)SkScalarToDouble(width), (int)SkScalarToDouble(height),
                     background);
#endif
        SkAutoTUnref<SkBaseDevice> device;
        if (strcmp(FLAGS_config[0], "8888") == 0) {
            device.reset(SkNEW_ARGS(SkBitmapDevice, (bitmap)));
        }
#if SK_SUPPORT_GPU
        else if (strcmp(FLAGS_config[0], "gpu") == 0) {
            SkAutoTUnref<GrSurface> target;
            GrContext* gr = gContextFactory.get(GrContextFactory::kNative_GLContextType);
            if (gr) {
                // create a render target to back the device
                GrTextureDesc desc;
                desc.fConfig = kSkia8888_GrPixelConfig;
                desc.fFlags = kRenderTarget_GrTextureFlagBit;
                desc.fWidth = SkScalarCeilToInt(width);
                desc.fHeight = SkScalarCeilToInt(height);
                desc.fSampleCnt = 0;
                target.reset(gr->createUncachedTexture(desc, NULL, 0));
            }
            if (NULL == target.get()) {
                SkASSERT(0);
                return false;
            }

            device.reset(SkGpuDevice::Create(target));
        }
#endif
        else {
            SkDebugf("unknown --config: %s\n", FLAGS_config[0]);
            return false;
        }
        SkCanvas canvas(device);

#ifdef PDF_TRACE_DIFF_IN_PNG
        gDumpBitmap = &bitmap;
        gDumpCanvas = &canvas;
#endif
        renderer.renderPage(page < 0 ? 0 : page, &canvas, rect);

        SkString outputPath;
        if (!make_output_filepath(&outputPath, outputDir, inputFilename, page)) {
            return false;
        }
        SkImageEncoder::EncodeFile(outputPath.c_str(), bitmap, SkImageEncoder::kPNG_Type, 100);

        if (FLAGS_showMemoryUsage) {
            SkDebugf("Memory usage after page %i rendered: %u\n",
                     page < 0 ? 0 : page, (unsigned int)renderer.bytesUsed());
        }
    }
    return true;
}