Imported Upstream version 0.7.0
[platform/upstream/libjxl.git] / experimental / fast_lossless / fast_lossless_main.cc
1 // Copyright (c) the JPEG XL Project Authors. All rights reserved.
2 //
3 // Use of this source code is governed by a BSD-style
4 // license that can be found in the LICENSE file.
5
6 #include <stdio.h>
7 #include <stdlib.h>
8 #include <string.h>
9
10 #include <chrono>
11 #include <thread>
12
13 #include "fast_lossless.h"
14 #include "lodepng.h"
15 #include "pam-input.h"
16
17 int main(int argc, char** argv) {
18   if (argc < 3) {
19     fprintf(stderr, "Usage: %s in.png out.jxl [effort] [num_reps]\n", argv[0]);
20     return 1;
21   }
22
23   const char* in = argv[1];
24   const char* out = argv[2];
25   int effort = argc >= 4 ? atoi(argv[3]) : 2;
26   size_t num_reps = argc >= 5 ? atoi(argv[4]) : 1;
27
28   if (effort < 0 || effort > 127) {
29     fprintf(
30         stderr,
31         "Effort should be between 0 and 127 (default is 2, more is slower)\n");
32     return 1;
33   }
34
35   unsigned char* png;
36   unsigned w, h;
37   size_t nb_chans = 4, bitdepth = 8;
38
39   unsigned error = lodepng_decode32_file(&png, &w, &h, in);
40
41   size_t width = w, height = h;
42   if (error && !DecodePAM(in, &png, &width, &height, &nb_chans, &bitdepth)) {
43     fprintf(stderr, "lodepng error %u: %s\n", error, lodepng_error_text(error));
44     return 1;
45   }
46
47   size_t encoded_size = 0;
48   unsigned char* encoded = nullptr;
49   size_t stride = width * nb_chans * (bitdepth > 8 ? 2 : 1);
50
51   auto start = std::chrono::high_resolution_clock::now();
52   for (size_t _ = 0; _ < num_reps; _++) {
53     free(encoded);
54     encoded_size = FastLosslessEncode(png, width, stride, height, nb_chans,
55                                       bitdepth, effort, &encoded);
56   }
57   auto stop = std::chrono::high_resolution_clock::now();
58   if (num_reps > 1) {
59     float us =
60         std::chrono::duration_cast<std::chrono::microseconds>(stop - start)
61             .count();
62     size_t pixels = size_t{width} * size_t{height} * num_reps;
63     float mps = pixels / us;
64     fprintf(stderr, "%10.3f MP/s\n", mps);
65     fprintf(stderr, "%10.3f bits/pixel\n",
66             encoded_size * 8.0 / float(width) / float(height));
67   }
68
69   FILE* o = fopen(out, "wb");
70   if (!o) {
71     fprintf(stderr, "error opening %s: %s\n", out, strerror(errno));
72     return 1;
73   }
74   if (fwrite(encoded, 1, encoded_size, o) != encoded_size) {
75     fprintf(stderr, "error writing to %s: %s\n", out, strerror(errno));
76   }
77   fclose(o);
78 }