build-graph 2.1.0 → 2.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- checksums.yaml.gz.sig +0 -0
- data/lib/build/graph/edge.rb +9 -20
- data/lib/build/graph/node.rb +15 -21
- data/lib/build/graph/task.rb +20 -20
- data/lib/build/graph/version.rb +7 -20
- data/lib/build/graph/walker.rb +44 -40
- data/lib/build/graph.rb +8 -27
- data/license.md +21 -0
- data/readme.md +37 -0
- data/releases.md +5 -0
- data.tar.gz.sig +0 -0
- metadata +48 -127
- metadata.gz.sig +0 -0
- data/.gitignore +0 -24
- data/.rspec +0 -4
- data/.travis.yml +0 -19
- data/Gemfile +0 -14
- data/README.md +0 -99
- data/Rakefile +0 -6
- data/build-graph.gemspec +0 -35
- data/spec/build/graph/build_test.rb +0 -85
- data/spec/build/graph/edge_spec.rb +0 -39
- data/spec/build/graph/graph_spec.rb +0 -172
- data/spec/build/graph/inherit_spec.rb +0 -51
- data/spec/build/graph/node_spec.rb +0 -80
- data/spec/build/graph/process_graph.rb +0 -89
- data/spec/build/graph/program/Benchmark.cpp +0 -72
- data/spec/build/graph/program/Benchmark.h +0 -65
- data/spec/build/graph/program/DictionarySort.h +0 -270
- data/spec/build/graph/program/ParallelMergeSort.h +0 -278
- data/spec/build/graph/program/main.cpp +0 -131
- data/spec/build/graph/task_spec.rb +0 -69
- data/spec/build/graph/walker_spec.rb +0 -125
- data/spec/spec_helper.rb +0 -13
|
@@ -1,172 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env rspec
|
|
2
|
-
# Copyright, 2012, by Samuel G. D. Williams. <http://www.codeotaku.com>
|
|
3
|
-
#
|
|
4
|
-
# Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
5
|
-
# of this software and associated documentation files (the "Software"), to deal
|
|
6
|
-
# in the Software without restriction, including without limitation the rights
|
|
7
|
-
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
8
|
-
# copies of the Software, and to permit persons to whom the Software is
|
|
9
|
-
# furnished to do so, subject to the following conditions:
|
|
10
|
-
#
|
|
11
|
-
# The above copyright notice and this permission notice shall be included in
|
|
12
|
-
# all copies or substantial portions of the Software.
|
|
13
|
-
#
|
|
14
|
-
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
15
|
-
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
16
|
-
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
17
|
-
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
18
|
-
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
19
|
-
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
|
20
|
-
# THE SOFTWARE.
|
|
21
|
-
|
|
22
|
-
require_relative 'process_graph'
|
|
23
|
-
|
|
24
|
-
RSpec.describe Build::Graph do
|
|
25
|
-
let(:group) {Process::Group.new}
|
|
26
|
-
|
|
27
|
-
it "shouldn't update mtime" do
|
|
28
|
-
test_glob = Build::Files::Glob.new(__dir__, "*.rb")
|
|
29
|
-
listing_output = Build::Files::Paths.directory(__dir__, ["listing.txt"])
|
|
30
|
-
|
|
31
|
-
FileUtils.rm_f listing_output.to_a
|
|
32
|
-
|
|
33
|
-
walker = Build::Graph::Walker.for(ProcessTask, group)
|
|
34
|
-
|
|
35
|
-
top = ProcessNode.top do
|
|
36
|
-
process test_glob, listing_output do
|
|
37
|
-
run("ls", "-la", *inputs, :out => outputs.first.for_writing)
|
|
38
|
-
end
|
|
39
|
-
end
|
|
40
|
-
|
|
41
|
-
group.wait do
|
|
42
|
-
walker.update(top)
|
|
43
|
-
end
|
|
44
|
-
|
|
45
|
-
first_modified_time = listing_output.first.modified_time
|
|
46
|
-
|
|
47
|
-
group.wait do
|
|
48
|
-
walker.update(top)
|
|
49
|
-
end
|
|
50
|
-
|
|
51
|
-
# The output file shouldn't have been changed because already exists and the input files haven't changed either:
|
|
52
|
-
second_modified_time = listing_output.first.modified_time
|
|
53
|
-
|
|
54
|
-
# The granularity of mtime on some systems is a bit weird:
|
|
55
|
-
expect(second_modified_time.to_f).to be_within(0.001).of(first_modified_time.to_f)
|
|
56
|
-
|
|
57
|
-
FileUtils.rm_f listing_output.to_a
|
|
58
|
-
walker.monitor.update(listing_output.roots)
|
|
59
|
-
|
|
60
|
-
# The granularity of modification times isn't that great, so we use >= below.
|
|
61
|
-
# sleep 1
|
|
62
|
-
|
|
63
|
-
group.wait do
|
|
64
|
-
walker.update(top)
|
|
65
|
-
end
|
|
66
|
-
|
|
67
|
-
expect(listing_output.first.modified_time).to be >= first_modified_time
|
|
68
|
-
|
|
69
|
-
FileUtils.rm_f listing_output.to_a
|
|
70
|
-
end
|
|
71
|
-
|
|
72
|
-
it "should compile program and respond to changes in source code" do
|
|
73
|
-
program_root = Build::Files::Path.join(__dir__, "program")
|
|
74
|
-
code_glob = Build::Files::Glob.new(program_root, "*.cpp")
|
|
75
|
-
program_path = Build::Files::Path.join(program_root, "dictionary-sort")
|
|
76
|
-
|
|
77
|
-
walker = Build::Graph::Walker.for(ProcessTask, group)
|
|
78
|
-
|
|
79
|
-
#FileUtils.touch(code_glob.first)
|
|
80
|
-
|
|
81
|
-
top = ProcessNode.top do
|
|
82
|
-
process code_glob, program_path do
|
|
83
|
-
object_files = inputs.with(extension: ".o") do |input_path, output_path|
|
|
84
|
-
depfile_path = input_path + ".d"
|
|
85
|
-
|
|
86
|
-
dependencies = Build::Files::Paths.new(input_path)
|
|
87
|
-
|
|
88
|
-
if File.exist? depfile_path
|
|
89
|
-
depfile = Build::Makefile.load_file(depfile_path)
|
|
90
|
-
|
|
91
|
-
dependencies = depfile[output_path] || dependencies
|
|
92
|
-
end
|
|
93
|
-
|
|
94
|
-
process dependencies, output_path do
|
|
95
|
-
run("clang++", "-MMD", "-O3",
|
|
96
|
-
"-o", output_path.shortest_path(input_path.root),
|
|
97
|
-
"-c", input_path.relative_path, "-std=c++11",
|
|
98
|
-
chdir: input_path.root
|
|
99
|
-
)
|
|
100
|
-
end
|
|
101
|
-
end
|
|
102
|
-
|
|
103
|
-
process object_files, program_path do
|
|
104
|
-
run("clang++", "-O3", "-o", program_path, *object_files.to_a, "-lm", "-pthread")
|
|
105
|
-
end
|
|
106
|
-
end
|
|
107
|
-
|
|
108
|
-
process program_path do
|
|
109
|
-
run("./" + program_path.relative_path, chdir: program_path.root)
|
|
110
|
-
end
|
|
111
|
-
end
|
|
112
|
-
|
|
113
|
-
group.wait do
|
|
114
|
-
walker.update(top)
|
|
115
|
-
end
|
|
116
|
-
|
|
117
|
-
expect(program_path).to be_exist
|
|
118
|
-
expect(code_glob.first.modified_time).to be <= program_path.modified_time
|
|
119
|
-
end
|
|
120
|
-
|
|
121
|
-
it "should copy files incrementally" do
|
|
122
|
-
program_root = Build::Files::Path.join(__dir__, "program")
|
|
123
|
-
files = Build::Files::Glob.new(program_root, "*.cpp")
|
|
124
|
-
destination = Build::Files::Path.new(__dir__) + "tmp"
|
|
125
|
-
|
|
126
|
-
walker = Build::Graph::Walker.for(ProcessTask, group)
|
|
127
|
-
|
|
128
|
-
top = ProcessNode.top files do
|
|
129
|
-
mkpath destination
|
|
130
|
-
|
|
131
|
-
inputs.each do |source_path|
|
|
132
|
-
destination_path = source_path.rebase(destination)
|
|
133
|
-
|
|
134
|
-
process source_path, destination_path do
|
|
135
|
-
$stderr.puts "Copying #{inputs.first} -> #{outputs.first}"
|
|
136
|
-
install inputs.first, outputs.first
|
|
137
|
-
end
|
|
138
|
-
end
|
|
139
|
-
end
|
|
140
|
-
|
|
141
|
-
mutex = Mutex.new
|
|
142
|
-
files_deleted = false
|
|
143
|
-
|
|
144
|
-
thread = Thread.new do
|
|
145
|
-
sleep 1
|
|
146
|
-
|
|
147
|
-
mutex.synchronize do
|
|
148
|
-
destination.glob("*.cpp").delete
|
|
149
|
-
|
|
150
|
-
files_deleted = true
|
|
151
|
-
end
|
|
152
|
-
end
|
|
153
|
-
|
|
154
|
-
walker.run do
|
|
155
|
-
mutex.synchronize do
|
|
156
|
-
group.wait do
|
|
157
|
-
walker.update(top)
|
|
158
|
-
end
|
|
159
|
-
end
|
|
160
|
-
|
|
161
|
-
break if files_deleted
|
|
162
|
-
end
|
|
163
|
-
|
|
164
|
-
thread.join
|
|
165
|
-
|
|
166
|
-
expect(destination).to be_exist
|
|
167
|
-
# This line failed, may still be a race condition:
|
|
168
|
-
expect(destination.glob("*.cpp").count).to be == 2
|
|
169
|
-
|
|
170
|
-
destination.delete
|
|
171
|
-
end
|
|
172
|
-
end
|
|
@@ -1,51 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env rspec
|
|
2
|
-
# Copyright, 2012, by Samuel G. D. Williams. <http://www.codeotaku.com>
|
|
3
|
-
#
|
|
4
|
-
# Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
5
|
-
# of this software and associated documentation files (the "Software"), to deal
|
|
6
|
-
# in the Software without restriction, including without limitation the rights
|
|
7
|
-
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
8
|
-
# copies of the Software, and to permit persons to whom the Software is
|
|
9
|
-
# furnished to do so, subject to the following conditions:
|
|
10
|
-
#
|
|
11
|
-
# The above copyright notice and this permission notice shall be included in
|
|
12
|
-
# all copies or substantial portions of the Software.
|
|
13
|
-
#
|
|
14
|
-
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
15
|
-
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
16
|
-
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
17
|
-
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
18
|
-
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
19
|
-
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
|
20
|
-
# THE SOFTWARE.
|
|
21
|
-
|
|
22
|
-
require 'build/graph/walker'
|
|
23
|
-
require 'build/graph/task'
|
|
24
|
-
require 'build/files'
|
|
25
|
-
|
|
26
|
-
RSpec.describe Build::Graph::Walker do
|
|
27
|
-
it "should inherit children outputs", :focus do
|
|
28
|
-
test_glob = Build::Files::Glob.new(__dir__, "*.rb")
|
|
29
|
-
listing_output = Build::Files::Paths.directory(__dir__, ["listing.txt"])
|
|
30
|
-
|
|
31
|
-
node_a = Build::Graph::Node.new(Build::Files::Paths::NONE, :inherit)
|
|
32
|
-
node_b = Build::Graph::Node.new(test_glob, listing_output)
|
|
33
|
-
|
|
34
|
-
walker = Build::Graph::Walker.new do |walker, node|
|
|
35
|
-
task = Build::Graph::Task.new(walker, node)
|
|
36
|
-
|
|
37
|
-
task.visit do
|
|
38
|
-
if node == node_a
|
|
39
|
-
task.invoke(node_b)
|
|
40
|
-
end
|
|
41
|
-
end
|
|
42
|
-
end
|
|
43
|
-
|
|
44
|
-
walker.update([node_a])
|
|
45
|
-
|
|
46
|
-
task_a = walker.tasks[node_a]
|
|
47
|
-
task_b = walker.tasks[node_b]
|
|
48
|
-
|
|
49
|
-
expect(task_a.outputs.to_a).to be == task_b.outputs.to_a
|
|
50
|
-
end
|
|
51
|
-
end
|
|
@@ -1,80 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env rspec
|
|
2
|
-
# Copyright, 2012, by Samuel G. D. Williams. <http://www.codeotaku.com>
|
|
3
|
-
#
|
|
4
|
-
# Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
5
|
-
# of this software and associated documentation files (the "Software"), to deal
|
|
6
|
-
# in the Software without restriction, including without limitation the rights
|
|
7
|
-
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
8
|
-
# copies of the Software, and to permit persons to whom the Software is
|
|
9
|
-
# furnished to do so, subject to the following conditions:
|
|
10
|
-
#
|
|
11
|
-
# The above copyright notice and this permission notice shall be included in
|
|
12
|
-
# all copies or substantial portions of the Software.
|
|
13
|
-
#
|
|
14
|
-
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
15
|
-
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
16
|
-
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
17
|
-
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
18
|
-
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
19
|
-
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
|
20
|
-
# THE SOFTWARE.
|
|
21
|
-
|
|
22
|
-
require 'build/graph/node'
|
|
23
|
-
require 'build/files/glob'
|
|
24
|
-
require 'build/files/system'
|
|
25
|
-
|
|
26
|
-
RSpec.describe Build::Graph::Node do
|
|
27
|
-
include Build::Graph
|
|
28
|
-
include Build::Files
|
|
29
|
-
|
|
30
|
-
let(:test_glob) {Build::Files::Glob.new(__dir__, "*.rb")}
|
|
31
|
-
let(:listing_output) {Build::Files::Paths.directory(__dir__, ["listing.txt"])}
|
|
32
|
-
|
|
33
|
-
it "should be unique" do
|
|
34
|
-
node_a = Build::Graph::Node.new(test_glob, listing_output)
|
|
35
|
-
node_b = Build::Graph::Node.new(listing_output, Build::Files::Paths::NONE)
|
|
36
|
-
|
|
37
|
-
expect(node_a).to be_eql node_a
|
|
38
|
-
expect(node_a).to_not be_eql node_b
|
|
39
|
-
|
|
40
|
-
node_c = Build::Graph::Node.new(test_glob, listing_output)
|
|
41
|
-
|
|
42
|
-
expect(node_a).to be_eql node_c
|
|
43
|
-
end
|
|
44
|
-
|
|
45
|
-
it "should be dirty" do
|
|
46
|
-
node_a = Build::Graph::Node.new(test_glob, listing_output)
|
|
47
|
-
|
|
48
|
-
expect(node_a.dirty?).to be true
|
|
49
|
-
end
|
|
50
|
-
|
|
51
|
-
it "should be clean" do
|
|
52
|
-
listing_output.first.touch
|
|
53
|
-
|
|
54
|
-
node_a = Build::Graph::Node.new(test_glob, listing_output)
|
|
55
|
-
|
|
56
|
-
expect(node_a.dirty?).to be false
|
|
57
|
-
|
|
58
|
-
listing_output.first.delete
|
|
59
|
-
end
|
|
60
|
-
|
|
61
|
-
it "should be dirty if input files are missing" do
|
|
62
|
-
input = Build::Files::Paths.directory(__dir__, ["missing-input.txt"])
|
|
63
|
-
output = Build::Files::Glob.new(__dir__, "*.rb")
|
|
64
|
-
|
|
65
|
-
node = Build::Graph::Node.new(input, output)
|
|
66
|
-
|
|
67
|
-
expect(node.missing?).to be true
|
|
68
|
-
expect(node.dirty?).to be true
|
|
69
|
-
end
|
|
70
|
-
|
|
71
|
-
it "should be dirty if output files are missing" do
|
|
72
|
-
input = Build::Files::Glob.new(__dir__, "*.rb")
|
|
73
|
-
output = Build::Files::Paths.directory(__dir__, ["missing-output.txt"])
|
|
74
|
-
|
|
75
|
-
node = Build::Graph::Node.new(input, output)
|
|
76
|
-
|
|
77
|
-
expect(node.missing?).to be true
|
|
78
|
-
expect(node.dirty?).to be true
|
|
79
|
-
end
|
|
80
|
-
end
|
|
@@ -1,89 +0,0 @@
|
|
|
1
|
-
|
|
2
|
-
require 'process/group'
|
|
3
|
-
require 'build/files'
|
|
4
|
-
require 'build/graph'
|
|
5
|
-
|
|
6
|
-
require 'console/event/spawn'
|
|
7
|
-
|
|
8
|
-
class ProcessNode < Build::Graph::Node
|
|
9
|
-
def initialize(inputs, outputs, block, title: nil)
|
|
10
|
-
super(inputs, outputs)
|
|
11
|
-
|
|
12
|
-
if title
|
|
13
|
-
@title = title
|
|
14
|
-
else
|
|
15
|
-
@title = block.source_location
|
|
16
|
-
end
|
|
17
|
-
|
|
18
|
-
@block = block
|
|
19
|
-
end
|
|
20
|
-
|
|
21
|
-
def == other
|
|
22
|
-
super and
|
|
23
|
-
@title == other.title and
|
|
24
|
-
@block == other.block
|
|
25
|
-
end
|
|
26
|
-
|
|
27
|
-
def hash
|
|
28
|
-
super ^ @title.hash ^ @block.hash
|
|
29
|
-
end
|
|
30
|
-
|
|
31
|
-
def evaluate(context)
|
|
32
|
-
context.instance_eval(&@block)
|
|
33
|
-
end
|
|
34
|
-
|
|
35
|
-
attr :title
|
|
36
|
-
end
|
|
37
|
-
|
|
38
|
-
class ProcessTask < Build::Graph::Task
|
|
39
|
-
def initialize(walker, node, group)
|
|
40
|
-
super(walker, node)
|
|
41
|
-
|
|
42
|
-
@group = group
|
|
43
|
-
end
|
|
44
|
-
|
|
45
|
-
def process(inputs, outputs = :inherit, **options, &block)
|
|
46
|
-
inputs = Build::Files::List.coerce(inputs)
|
|
47
|
-
outputs = Build::Files::List.coerce(outputs) unless outputs.kind_of? Symbol
|
|
48
|
-
|
|
49
|
-
node = ProcessNode.new(inputs, outputs, block, **options)
|
|
50
|
-
|
|
51
|
-
self.invoke(node)
|
|
52
|
-
end
|
|
53
|
-
|
|
54
|
-
def wet?
|
|
55
|
-
@node.dirty?
|
|
56
|
-
end
|
|
57
|
-
|
|
58
|
-
def run(*arguments)
|
|
59
|
-
if wet?
|
|
60
|
-
@walker.logger.debug(self) {Console::Event::Spawn.for(*arguments)}
|
|
61
|
-
|
|
62
|
-
status = @group.spawn(*arguments)
|
|
63
|
-
|
|
64
|
-
if status != 0
|
|
65
|
-
raise CommandError.new(status)
|
|
66
|
-
end
|
|
67
|
-
end
|
|
68
|
-
end
|
|
69
|
-
|
|
70
|
-
def mkpath(*args)
|
|
71
|
-
return unless wet?
|
|
72
|
-
|
|
73
|
-
FileUtils.mkpath(*args)
|
|
74
|
-
end
|
|
75
|
-
|
|
76
|
-
def install(*args)
|
|
77
|
-
return unless wet?
|
|
78
|
-
|
|
79
|
-
FileUtils.install(*args)
|
|
80
|
-
end
|
|
81
|
-
|
|
82
|
-
# This function is called to finish the invocation of the task within the graph.
|
|
83
|
-
# There are two possible ways this function can generally proceed.
|
|
84
|
-
# 1/ The node this task is running for is clean, and thus no actual processing needs to take place, but children should probably be executed.
|
|
85
|
-
# 2/ The node this task is running for is dirty, and the execution of commands should work as expected.
|
|
86
|
-
def update
|
|
87
|
-
@node.evaluate(self)
|
|
88
|
-
end
|
|
89
|
-
end
|
|
@@ -1,72 +0,0 @@
|
|
|
1
|
-
//
|
|
2
|
-
// Benchmark.cpp
|
|
3
|
-
// DictionarySort
|
|
4
|
-
//
|
|
5
|
-
// Created by Samuel Williams on 2/11/11.
|
|
6
|
-
// Copyright, 2014, by Samuel G. D. Williams. <http://www.codeotaku.com>
|
|
7
|
-
//
|
|
8
|
-
|
|
9
|
-
#include "Benchmark.h"
|
|
10
|
-
|
|
11
|
-
#include <sys/time.h>
|
|
12
|
-
|
|
13
|
-
// A timer class for quickly checking the wall-clock performance of code.
|
|
14
|
-
namespace Benchmark
|
|
15
|
-
{
|
|
16
|
-
static TimeT system_time () {
|
|
17
|
-
static struct timeval t;
|
|
18
|
-
gettimeofday (&t, (struct timezone*)0);
|
|
19
|
-
return ((TimeT)t.tv_sec) + ((TimeT)t.tv_usec / 1000000.0);
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
WallTime::WallTime () {
|
|
23
|
-
this->reset();
|
|
24
|
-
}
|
|
25
|
-
|
|
26
|
-
void WallTime::reset () {
|
|
27
|
-
this->_last = system_time();
|
|
28
|
-
this->_total = 0.0;
|
|
29
|
-
}
|
|
30
|
-
|
|
31
|
-
TimeT WallTime::total () const {
|
|
32
|
-
TimeT current = system_time();
|
|
33
|
-
this->_total += current - this->_last;
|
|
34
|
-
this->_last = current;
|
|
35
|
-
return this->_total;
|
|
36
|
-
}
|
|
37
|
-
|
|
38
|
-
ProcessorTime::ProcessorTime()
|
|
39
|
-
{
|
|
40
|
-
this->reset();
|
|
41
|
-
}
|
|
42
|
-
|
|
43
|
-
void ProcessorTime::reset ()
|
|
44
|
-
{
|
|
45
|
-
this->_last = std::clock();
|
|
46
|
-
this->_total = 0;
|
|
47
|
-
}
|
|
48
|
-
|
|
49
|
-
TimeT ProcessorTime::total () const
|
|
50
|
-
{
|
|
51
|
-
std::clock_t current = std::clock();
|
|
52
|
-
this->_total += std::clock() - this->_last;
|
|
53
|
-
this->_last = current;
|
|
54
|
-
|
|
55
|
-
return TimeT(this->_total) / TimeT(CLOCKS_PER_SEC);
|
|
56
|
-
}
|
|
57
|
-
|
|
58
|
-
Timer::Timer()
|
|
59
|
-
{
|
|
60
|
-
}
|
|
61
|
-
|
|
62
|
-
void Timer::reset ()
|
|
63
|
-
{
|
|
64
|
-
_wall_time.reset();
|
|
65
|
-
_processor_time.reset();
|
|
66
|
-
}
|
|
67
|
-
|
|
68
|
-
Timer::Sample Timer::sample() const
|
|
69
|
-
{
|
|
70
|
-
return {_wall_time.total(), _processor_time.total()};
|
|
71
|
-
}
|
|
72
|
-
}
|
|
@@ -1,65 +0,0 @@
|
|
|
1
|
-
//
|
|
2
|
-
// Benchmark.h
|
|
3
|
-
// DictionarySort
|
|
4
|
-
//
|
|
5
|
-
// Created by Samuel Williams on 2/11/11.
|
|
6
|
-
// Copyright, 2014, by Samuel G. D. Williams. <http://www.codeotaku.com>
|
|
7
|
-
//
|
|
8
|
-
|
|
9
|
-
#pragma once
|
|
10
|
-
|
|
11
|
-
#include <ctime>
|
|
12
|
-
|
|
13
|
-
// A timer class for quickly checking the wall-clock performance of code.
|
|
14
|
-
namespace Benchmark
|
|
15
|
-
{
|
|
16
|
-
typedef double TimeT;
|
|
17
|
-
|
|
18
|
-
class WallTime {
|
|
19
|
-
protected:
|
|
20
|
-
mutable TimeT _last, _total;
|
|
21
|
-
|
|
22
|
-
public:
|
|
23
|
-
WallTime ();
|
|
24
|
-
|
|
25
|
-
void reset ();
|
|
26
|
-
TimeT total () const;
|
|
27
|
-
};
|
|
28
|
-
|
|
29
|
-
class ProcessorTime {
|
|
30
|
-
protected:
|
|
31
|
-
mutable std::clock_t _last, _total;
|
|
32
|
-
|
|
33
|
-
public:
|
|
34
|
-
ProcessorTime();
|
|
35
|
-
|
|
36
|
-
void reset ();
|
|
37
|
-
TimeT total () const;
|
|
38
|
-
};
|
|
39
|
-
|
|
40
|
-
class Timer {
|
|
41
|
-
protected:
|
|
42
|
-
WallTime _wall_time;
|
|
43
|
-
ProcessorTime _processor_time;
|
|
44
|
-
|
|
45
|
-
public:
|
|
46
|
-
Timer();
|
|
47
|
-
|
|
48
|
-
const WallTime & wall_time() const { return _wall_time; }
|
|
49
|
-
const ProcessorTime & processor_time() const { return _processor_time; }
|
|
50
|
-
|
|
51
|
-
void reset ();
|
|
52
|
-
|
|
53
|
-
struct Sample {
|
|
54
|
-
TimeT wall_time_total;
|
|
55
|
-
TimeT processor_time_total;
|
|
56
|
-
|
|
57
|
-
TimeT approximate_processor_usage() const {
|
|
58
|
-
return processor_time_total / wall_time_total;
|
|
59
|
-
}
|
|
60
|
-
};
|
|
61
|
-
|
|
62
|
-
Sample sample() const;
|
|
63
|
-
};
|
|
64
|
-
|
|
65
|
-
}
|