• Home
Name Date Size #Lines LOC

..--

example/03-May-2024-773748

include/ditto/03-May-2024-1,128612

schema/03-May-2024-169141

src/03-May-2024-2,1391,485

test/03-May-2024-1,5621,029

.clang-formatD03-May-2024239 1211

.gitignoreD03-May-20248 21

Android.bpD03-May-20241.9 KiB9587

AndroidTest.xmlD03-May-20241.4 KiB2914

CMakeLists.txtD03-May-2024674 3927

LICENSED03-May-202411.1 KiB203169

OWNERSD03-May-202480 54

README.mdD03-May-202413.9 KiB451339

dittobench.cppD03-May-20241.5 KiB5330

dittobench_benchmark.cppD03-May-20242.7 KiB7747

dittotrace.cppD03-May-20248.3 KiB223138

README.md

1# Dittosuite
2
3Dittosuite is a work in progress collection of tools that aims at providing
4a high-level language called Dittolang that defines operations.
5
6The defined Dittolang operations can be interpreted by Dittosim for simulation
7to provide a simulated performance measurement and quickly identify
8the goodness of a solution.
9
10Specularly, Dittobench interprets the Dittolang operations and executes them on
11a real device, tracking the behavior and measuring the performance.
12
13# How to run
14
15```
16$ ./dittobench [options] [.ditto file]
17```
18
19To run a benchmark, a well formed .ditto file must be provided, see section
20[How to write .ditto files](#how-to-write-ditto-files)
21In addition, these options can be set:
22
23- `--results-output=<int | string>` (default: report). Select the results output format.
24Options: report, csv with 0, 1 respectively.
25- `--log-stream=<int | string>` (default: stdout). Select the output stream for the log messages.
26Options: stdout, logcat with 0, 1 respectively.
27- `--log-level=<int | string>` (default: INFO). Select to output messages which are at or below
28the set level. Options: VERBOSE, DEBUG, INFO, WARNING, ERROR, FATAL with 0, 1, 2, 3, 4 and 5
29respectively.
30- `--parameters=string`. If the benchmark is parametric, all the parameters (separated by commas)
31can be given through this option.
32
33# How to write .ditto files
34
35Every .ditto file should begin with this skeleton:
36```
37main: {
38  ...
39},
40global {
41  ...
42}
43```
44
45Optionally, it can contain `init` and `clean_up` sections:
46```
47init: {
48  ...
49},
50main: {
51  ...
52},
53clean_up: {
54  ...
55},
56global {
57  ...
58}
59```
60
61## `global`
62
63Global section should contain general benchmark configuration. Currently available options:
64
65- (optional) `string absolute_path` (`default = ""`). Specifies the absolute path for the files.
66
67## `init`
68
69`init` is optional and can be used to initialize the benchmarking environment. It executes
70instructions similar to `main`, but the results are not collected in the end.
71
72## `main`
73
74`main` is the entry point for the benchmark. It can contain a single `instruction` or
75`instruction_set` (also with nested `instruction_set`).
76
77## `clean_up`
78
79`clean_up` is optional and can be used to reset the benchmarking environment to the initial state,
80e.g, delete benchmark files. Similar to `init`, it executes instructions like `main`, but results
81are not collected in the end.
82
83## `instruction`
84
85```
86{
87  <name of the instruction>: {
88    <first argument>,
89    <second argument>,
90    ...
91  },
92  <general instruction options>
93}
94```
95
96Currently available options:
97- (optional) `int repeat` (`default = 1`). Specifies how many times the instruction should be
98repeated.
99
100## `instruction_set`
101```
102{
103  instruction_set: {
104    instructions: {
105      {
106        <name of the first instruction>: {
107          <first argument>,
108          <second argument>,
109          ...
110        },
111        <general instruction options>
112      },
113      {
114        <name of the second instruction>: {
115          <first argument>,
116          <second argument>,
117          ...
118        },
119        <general instruction options>
120      },
121      ...
122    },
123    iterate_options: {...}
124  },
125  <general instruction options>
126}
127```
128
129Instruction set is an Instruction container that executes the contained instructions sequentially.
130Instruction set can optionally iterate over a list and execute the provided set of instructions on
131each item from the list. To use it, `iterate_options` should be set with these options:
132- `string list_name` - Shared variable name pointing to a list of values.
133- `string item_name` - Shared variable name to which a selected value should be stored.
134- (optional) `Order order` (`default = SEQUENTIAL`) - Specifies if
135  the elements of the list should be accessed sequentially or randomly. Options:
136  `SEQUENTIAL`, `RANDOM`.
137- (optional) `Reseeding reseeding` (`default = ONCE`) - Specifies how often the random number
138generator should be reseeded with the same provided (or generated) seed. Options: `ONCE`,
139`EACH_ROUND_OF_CYCLES`, `EACH_CYCLE`.
140- (optional) `uint32 seed` - Seed for the random number generator. If the seed is not provided,
141current system time is used as the seed.
142
143## `multithreading` and `threads`
144
145```
146multithreading: {
147  threads: [
148    {
149      instruction: {...},
150      spawn: <number of threads to spawn with the provided instruction>
151    },
152    ...
153  ]
154}
155```
156
157Multithreading is another instruction container that executes the specified instructions
158(or instruction sets) in different threads. If the optional `spawn` option for a specific
159instruction (or instruction set) is provided, then the provided number of threads will be created
160for it.
161
162## Example
163
164```
165main: {
166  instruction_set: {
167    instructions: [
168      {
169        open_file: {
170          path_name: "newfile2.txt",
171          output_fd: "test_file"
172        }
173      },
174      {
175        close_file: {
176          input_fd: "test_file"
177        }
178      }
179    ]
180  },
181  repeat: 10
182},
183global {
184  absolute_path: "/data/local/tmp/";
185}
186```
187See more examples in `example/`.
188
189# Predefined list of instructions
190
191## `open_file`
192
193Opens the file with a file path or a shared variable name pointing to a file path. If neither of
194those are provided, a random name consisting of 9 random digits is generated. Optionally saves the
195file descriptor which can then be used by subsequent instructions. Also, can optionally create the
196file if it does not already exist.
197
198### Arguments:
199- (optional) `string path_name` - Specifies the file path.<br/>
200OR<br/>
201`string input` - Shared variable name pointing to a file path.
202- (optional) `string output_fd` - Shared variable name to which output file descriptor
203should be saved.
204- (optional) `bool create` (`default = true`) - Specifies if the file should be created if it does
205not already exist. If the file exists, nothing happens.
206
207## `delete_file`
208
209Deletes the file with a file path or a shared variable name pointing to a file path.
210Uses `unlink(2)`.
211
212### Arguments:
213- `string path_name` - Specifies the file path.<br/>
214OR<br/>
215`string input` - Shared variable name pointing to a file path.
216
217
218## `close_file`
219
220Closes the file with the provided file descriptor.
221Uses `close(2)`.
222
223### Arguments:
224- `string input_fd` - Shared variable name pointing to a file descriptor.
225
226## `resize_file`
227
228Resizes the file with the provided file descriptor and new size. If the provided size is greater
229than the current file size, `fallocate(2)` is used, while `ftruncate(2)` is used if the provided
230size is not greater than the current file size.
231
232### Arguments:
233- `string input_fd` - Shared variable name pointing to a file descriptor.
234- `int64 size` - New file size (in bytes).
235
236## `resize_file_random`
237
238Resizes the file with the provided file descriptor and a range for new size. New file size is
239randomly generated in the provided range and if the generated size is greater
240than the current file size, `fallocate(2)` is used, while `ftruncate(2)` is used if the generated
241size is not greater than the current file size.
242
243### Arguments:
244- `string input_fd` - Shared variable name pointing to a file descriptor.
245- `int64 min` - Minimum value (in bytes)
246- `int64 max` - Maximum value (in bytes)
247- (optional) `uint32 seed` - Seed for the random number generator. If the seed is not provided,
248current system time is used as the seed.
249- (optional) `Reseeding reseeding` (`default = ONCE`). How often the random number
250generator should be reseeded with the provided (or generated) seed. Options: `ONCE`,
251`EACH_ROUND_OF_CYCLES`, `EACH_CYCLE`.
252
253## `write_file`
254
255Writes to file with the provided file descriptor. For `SEQUENTIAL`
256access, the blocks of data will be written sequentially and if the end of
257the file is reached, new blocks will start from the beginning of the file. For
258`RANDOM` access, the block offset, to which data should be written, will
259be randomly chosen with uniform distribution. `10101010` byte is used for the
260write operation to fill the memory with alternating ones and zeroes. Uses
261`pwrite64(2)`.
262
263### Arguments:
264- `string input_fd` - Shared variable name pointing to a file descriptor.
265- (optional) `int64 size` (`default = -1`) - How much data (in bytes) should be written in total.
266If it is set to `-1`, then file size is used.
267- (optional) `int64 block_size` (`default = 4096`) - How much data (in bytes) should be written at
268once. If it is set to `-1`, then file size is used.
269- (optional) `int64 starting_offset` (`default = 0`) - If `access_order` is
270  set to `SEQUENTIAL`, then the blocks, to which the data should be written,
271  will start from this starting offset (in bytes).
272- (optional) `Order access_order` (`default = SEQUENTIAL`) - Order of the
273  write. Options: `SEQUENTIAL` and `RANDOM`.
274- (optional) `uint32 seed` - Seed for the random number generator. If the seed is not provided,
275current system time is used as the seed.
276- (optional) `bool fsync` (`default = false`) - If set, `fsync(2)` will be called after the
277execution of all write operations.
278- (optional) `Reseeding reseeding` (`default = ONCE`) - How often the random number
279generator should be reseeded with the provided (or generated) seed. Options: `ONCE`,
280`EACH_ROUND_OF_CYCLES`, `EACH_CYCLE`.
281
282## `read_file`
283
284Reads from file with the provided file descriptor. For `SEQUENTIAL`
285access, the blocks of data will be read sequentially and if the end of
286the file is reached, new blocks will start from the beginning of the file. For
287`RANDOM` access, the block offset, from which data should be read, will
288be randomly chosen with uniform distribution. Calls `posix_fadvise(2)` before
289the read operations. Uses `pread64(2)`.
290
291### Arguments:
292- `string input_fd` - Shared variable name pointing to a file descriptor.
293- (optional) `int64 size` (`default = -1`) - How much data (in bytes) should be read in total.
294If it is set to `-1`, then file size is used.
295- (optional) `int64 block_size` (`default = 4096`) - How much data (in bytes) should be read at
296once. If it is set to `-1`, then file size is used.
297- (optional) `int64 starting_offset` (`default = 0`) - If `access_order` is
298  set to `SEQUENTIAL`, then the blocks, from which the data should be read,
299  will start from this starting offset (in bytes).
300- (optional) `Order access_order` (`default = SEQUENTIAL`) - Order of the
301  read. Options: `SEQUENTIAL` and `RANDOM`.
302- (optional) `uint32 seed` - Seed for the random number generator. If the seed is not provided,
303current system time is used as the seed.
304- (optional) `ReadFAdvise fadvise` (`default = AUTOMATIC`) - Sets the argument
305  for the `posix_fadvise(2)` operation. Options: `AUTOMATIC`, `NORMAL`,
306  `SEQUENTIAL` and `RANDOM`. If `AUTOMATIC` is set, then
307  `POSIX_FADV_SEQUENTIAL` or `POSIX_FADV_RANDOM` will be used for `SEQUENTIAL`
308  and `RANDOM` access order respectively.
309- (optional) `Reseeding reseeding` (`default = ONCE`) - How often the random number
310generator should be reseeded with the provided (or generated) seed. Options: `ONCE`,
311`EACH_ROUND_OF_CYCLES`, `EACH_CYCLE`.
312
313## `read_directory`
314
315Reads file names from a directory and stores them as a list in a shared variable. Uses `readdir(3)`.
316
317### Arguments:
318- `string directory_name` - Name of the directory
319- `string output` - Shared variable name to which files names should be saved.
320
321## `invalidate_cache`
322
323Drops kernel clean caches, including, dentry, inode and page caches by calling sync() first and
324then writing `3` to `/proc/sys/vm/drop_caches`. No arguments.
325
326# Dependencies
327
328## Android
329
330The project is currently being developed as part of the Android Open Source
331Project (AOSP) and is supposed to run out-of-the-box.
332
333## Linux
334
335The following utilities are required to build the project on Linux:
336
337```
338sudo apt install cmake protobuf-compiler
339
340```
341
342# Testing
343
344## Linux
345
346A suite of unit tests is provided in the test/ directory.
347In Linux these tests can be run with the following commands:
348
349```
350mkdir build
351cd build
352make
353cd test
354ctest
355```
356
357
358# Use cases
359
360
361## File operations performance (high priority)
362
363Bandwidth and measurement when dealing with few huge files or many small files.
364Operations are combinations of sequential/random-offset read/write.
365
366Latency in creating/deleting files/folders.
367
368These operations should be able to be triggered in a multiprogrammed fashion.
369
370
371## Display pipeline
372
373A graph of processes that are communicating with each others in a pipeline of
374operations that are parallely contributing to the generation of display frames.
375
376
377## Scheduling (low priority)
378
379Spawning tasks (period, duration, deadline) and verifying their scheduling
380latency and deadline misses count.
381
382
383# Workflow example and implementation nits
384
385In the following scenario, two threads are running.
386
387T1 runs the following operations: Read, Write, Read, sends a request to T2 and
388waits for the reply, then Write, Read.
389T2 waits for a request, then Read, Write, then sends the reply to the requester.
390
391Operations are encoded as primitives expressed with ProtoBuffers.
392The definition of dependencies among threads can be represented as graphs.
393
394
395## Initialization phase
396
397The first graph traversal is performed at initialization time, when all the
398ProtoBuffer configuration files are distributed among all the binaries so that
399they can perform all the heavy initialization duties.
400
401
402## Execution phase
403
404After the initialization phase completes the graph can be traversed again to
405put all the workloads in execution.
406
407
408## Results gathering phase
409
410A final graph traversal can be performed to fetch all the measurements that
411each entity internally stored.
412
413
414## Post processing
415
416All the measurements must be ordered and later processed to provide useful
417information to the user.
418
419T1: INIT   : [ RD WR RD ]  SND               RCV [ WR RD ] : END
420T2:   INIT :                 RCV [ RD WR ] SND             :   END
421
422
423# Scratch notes
424
425critical path [ READ WRITE READ ] [ READ WRITE ]  [ WRITE READ ]
426-------------------->
427             >                  <
428Thread1   III-XXXXXX|X-SSSSSS-XX-TTTT
429Thread2               III-XXXX|XXX-TTTT
430                     ^
431
432       >       XXXXXXX    XX<
433                      XXXX
434
435
436READ WRITE READ
437
438--->
439
440vector<instr*> {read(), write(), read()};
441-> start()
442
443
444RECEIVE READ WRITE READ SEND
445--->
446vector<instr*> {receive(), read(), write(), read(), send()};
447start()
448
449lock on receive()
450
451