Tor 0.4.9.2-alpha-dev
All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Macros Modules Pages
bench.c
1/* Copyright (c) 2020 tevador <tevador@gmail.com> */
2/* See LICENSE for licensing information */
3
4#include "test_utils.h"
5#include "hashx_thread.h"
6#include "hashx_endian.h"
7#include "hashx_time.h"
8#include <assert.h>
9#include <limits.h>
10#include <inttypes.h>
11
12typedef struct worker_job {
13 int id;
14 hashx_thread thread;
15 hashx_ctx* ctx;
16 int64_t total_hashes;
17 uint64_t best_hash;
18 uint64_t threshold;
19 int start;
20 int step;
21 int end;
22 int nonces;
24
25static hashx_thread_retval worker(void* args) {
26 worker_job* job = (worker_job*)args;
27 job->total_hashes = 0;
28 job->best_hash = UINT64_MAX;
29 for (int seed = job->start; seed < job->end; seed += job->step) {
30 {
31 hashx_result result = hashx_make(job->ctx, &seed, sizeof(seed));
32 if (result == HASHX_FAIL_SEED) {
33 continue;
34 }
35 if (result == HASHX_FAIL_COMPILE) {
36 printf("Error: not supported. Try with --interpret\n");
37 }
38 assert(result == HASHX_OK);
39 if (result != HASHX_OK)
40 break;
41 }
42 for (int nonce = 0; nonce < job->nonces; ++nonce) {
43 uint8_t hash[HASHX_SIZE] = { 0 };
44 {
45#ifndef HASHX_BLOCK_MODE
46 hashx_result result = hashx_exec(job->ctx, nonce, hash);
47#else
48 hashx_result result = hashx_exec(job->ctx,
49 &nonce, sizeof(nonce), hash);
50#endif
51 assert(result == HASHX_OK);
52 if (result != HASHX_OK)
53 break;
54 }
55 uint64_t hashval = load64(hash);
56 if (hashval < job->best_hash) {
57 job->best_hash = hashval;
58 }
59 if (hashval < job->threshold) {
60 printf("[thread %2i] Hash (%5i, %5i) below threshold:"
61 " ...%02x%02x%02x%02x%02x%02x%02x%02x\n",
62 job->id,
63 seed,
64 nonce,
65 hash[0],
66 hash[1],
67 hash[2],
68 hash[3],
69 hash[4],
70 hash[5],
71 hash[6],
72 hash[7]);
73 }
74 }
75 job->total_hashes += job->nonces;
76 }
77 return HASHX_THREAD_SUCCESS;
78}
79
80int main(int argc, char** argv) {
81 int nonces, seeds, start, diff, threads;
82 bool interpret;
83 read_int_option("--diff", argc, argv, &diff, INT_MAX);
84 read_int_option("--start", argc, argv, &start, 0);
85 read_int_option("--seeds", argc, argv, &seeds, 500);
86 read_int_option("--nonces", argc, argv, &nonces, 65536);
87 read_int_option("--threads", argc, argv, &threads, 1);
88 read_option("--interpret", argc, argv, &interpret);
89 hashx_type ctx_type = HASHX_TYPE_INTERPRETED;
90 if (!interpret) {
91 ctx_type = HASHX_TYPE_COMPILED;
92 }
93 uint64_t best_hash = UINT64_MAX;
94 uint64_t diff_ex = (uint64_t)diff * 1000ULL;
95 uint64_t threshold = UINT64_MAX / diff_ex;
96 int seeds_end = seeds + start;
97 int64_t total_hashes = 0;
98 printf("Interpret: %i, Target diff.: %" PRIu64 ", Threads: %i\n", interpret, diff_ex, threads);
99 printf("Testing seeds %i-%i with %i nonces each ...\n", start, seeds_end - 1, nonces);
100 double time_start, time_end;
101 worker_job* jobs = malloc(sizeof(worker_job) * threads);
102 if (jobs == NULL) {
103 printf("Error: memory allocation failure\n");
104 return 1;
105 }
106 for (int thd = 0; thd < threads; ++thd) {
107 jobs[thd].ctx = hashx_alloc(ctx_type);
108 if (jobs[thd].ctx == NULL) {
109 printf("Error: memory allocation failure\n");
110 return 1;
111 }
112 jobs[thd].id = thd;
113 jobs[thd].start = start + thd;
114 jobs[thd].step = threads;
115 jobs[thd].end = seeds_end;
116 jobs[thd].nonces = nonces;
117 jobs[thd].threshold = threshold;
118 }
119 time_start = hashx_time();
120 if (threads > 1) {
121 for (int thd = 0; thd < threads; ++thd) {
122 jobs[thd].thread = hashx_thread_create(&worker, &jobs[thd]);
123 }
124 for (int thd = 0; thd < threads; ++thd) {
125 hashx_thread_join(jobs[thd].thread);
126 }
127 }
128 else {
129 worker(jobs);
130 }
131 time_end = hashx_time();
132 for (int thd = 0; thd < threads; ++thd) {
133 total_hashes += jobs[thd].total_hashes;
134 if (jobs[thd].best_hash < best_hash) {
135 best_hash = jobs[thd].best_hash;
136 }
137 }
138 double elapsed = time_end - time_start;
139 printf("Total hashes: %" PRIi64 "\n", total_hashes);
140 printf("%f hashes/sec.\n", total_hashes / elapsed);
141 printf("%f seeds/sec.\n", seeds / elapsed);
142 printf("Best hash: ...");
143 output_hex((char*)&best_hash, sizeof(best_hash));
144 printf(" (diff: %" PRIu64 ")\n", UINT64_MAX / best_hash);
145 free(jobs);
146 return 0;
147}
int main(int argc, char *argv[])
Definition: tor_main.c:25