Skip to content

Commit cf085da

Browse files
committed
Now with debugging!
In addition to refactoring the output formatting in general, there's now a separate --debug option that will provide you with even *more* obsessive detail about what's going on.
1 parent 87d1ba5 commit cf085da

File tree

1 file changed

+53
-35
lines changed

1 file changed

+53
-35
lines changed

bin/lvmsync

Lines changed: 53 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -43,10 +43,13 @@ def main()
4343
end
4444

4545
opts.on("-v", "--[no-]verbose",
46-
"Run verbosely") { |v| options[:verbose] = v }
46+
"Run verbosely") { |v| $verbose = v }
47+
48+
opts.on("-d", "--[no-]debug",
49+
"Print debugging information") { |v| $debug = v }
4750

4851
opts.on("-q", "--[no-]quiet",
49-
"Run quietly") { |v| options[:quiet] = v }
52+
"Run quietly") { |v| $quiet = v }
5053

5154
opts.on("-b <file>", "--snapback <file>",
5255
"Make a backup snapshot file on the destination") do |v|
@@ -75,49 +78,42 @@ def main()
7578
puts "lvmsync #{GVB.version}"
7679
exit 0
7780
rescue GVB::VersionUnobtainable
78-
$stderr.puts "Unable to determine lvmsync version."
79-
$stderr.puts "Install lvmsync as a gem, or run it from within a git checkout"
80-
exit 1
81+
fatal "Unable to determine lvmsync version.\n" +
82+
"Install lvmsync as a gem, or run it from within a git checkout"
8183
end
8284
end
8385
end.parse!
8486

85-
if options[:quiet] and options[:verbose]
86-
$stderr.puts "I can't run quietly *and* verbosely at the same time!"
87-
exit 1
87+
if $quiet and ($verbose or $debug)
88+
fatal "I can't run quietly *and* verbosely at the same time!"
8889
end
8990

9091
if options[:apply]
9192
if ARGV[0].nil?
92-
$stderr.puts "No destination device specified."
93-
exit 1
93+
fatal "No destination device specified."
9494
end
9595
options[:device] = ARGV[0]
9696
run_apply(options)
9797
elsif options[:server]
98-
$stderr.puts "--server is deprecated; please use '--apply -' instead" unless opts[:quiet]
98+
info "--server is deprecated; please use '--apply -' instead"
9999
if (ARGV[0].nil?)
100-
$stderr.puts "No destination block device specified. WTF?"
101-
exit 1
100+
fatal "No destination block device specified. WTF?"
102101
end
103102
options[:apply] = '-'
104103
options[:device] = ARGV[0]
105104
run_apply(options)
106105
else
107106
if ARGV[0].nil?
108-
$stderr.puts "ERROR: No snapshot specified. Exiting."
109-
exit 1
107+
fatal "No snapshot specified. Exiting. Do you need --help?"
110108
end
111109
options[:snapdev] = ARGV[0]
112110

113111
if options[:stdout] and options[:snapback]
114-
$stderr.puts "--snapback cannot be used with --stdout"
115-
exit 1
112+
fatal "--snapback cannot be used with --stdout"
116113
end
117114

118115
if (options[:stdout].nil? and ARGV[1].nil?)
119-
$stderr.puts "No destination specified."
120-
exit 1
116+
fatal "No destination specified."
121117
end
122118
if options[:stdout].nil?
123119
dev, host = ARGV[1].split(':', 2).reverse
@@ -143,18 +139,19 @@ end
143139
def process_dumpdata(instream, destdev, snapback = nil, opts = {})
144140
handshake = instream.readline.chomp
145141
unless handshake == PROTOCOL_VERSION
146-
$stderr.puts "Handshake failed; protocol mismatch? (saw '#{handshake}' expected '#{PROTOCOL_VERSION}'"
147-
exit 1
142+
fatal "Handshake failed; protocol mismatch? (saw '#{handshake}' expected '#{PROTOCOL_VERSION}'"
148143
end
149144

150145
snapback.puts handshake if snapback
151146

147+
verbose "Writing changed data to #{destdev.inspect}"
152148
File.open(destdev, 'w+') do |dest|
153149
while header = instream.read(12)
154150
offset, chunksize = header.unpack("QN")
155151
offset = ntohq(offset)
156152

157153
begin
154+
debug "Seeking to #{offset}"
158155
dest.seek offset
159156
rescue Errno::EINVAL
160157
# In certain rare circumstances, we want to transfer a block
@@ -164,6 +161,8 @@ def process_dumpdata(instream, destdev, snapback = nil, opts = {})
164161
# if you didn't notice that your dd shit itself, it's unlikely
165162
# you're going to notice now.
166163

164+
info "Write occured past end of device"
165+
167166
# Skip the chunk of data
168167
instream.read(chunksize)
169168
# Go to the next chunk
@@ -173,9 +172,12 @@ def process_dumpdata(instream, destdev, snapback = nil, opts = {})
173172
if snapback
174173
snapback.write(header)
175174
snapback.write dest.read(chunksize)
175+
# Got to back to where we were before, since the read from dest
176+
# has advanced the file pointer by `chunksize`
176177
dest.seek offset
177178
end
178179
dest.write instream.read(chunksize)
180+
debug "Wrote #{chunksize} bytes at #{offset}"
179181
end
180182
end
181183
end
@@ -189,13 +191,11 @@ def run_client(opts)
189191
lv = begin
190192
LVM::LogicalVolume.new(snapshot)
191193
rescue RuntimeError => e
192-
$stderr.puts "#{snapshot}: could not find logical volume (#{e.message})"
193-
exit 1
194+
fatal "#{snapshot}: could not find logical volume (#{e.message})"
194195
end
195196

196197
unless lv.snapshot?
197-
$stderr.puts "#{snapshot}: Not a snapshot device"
198-
exit 1
198+
fatal "#{snapshot}: Not a snapshot device"
199199
end
200200

201201
# Since, in principle, we're not supposed to be reading from snapshot
@@ -208,14 +208,16 @@ def run_client(opts)
208208
snapback = opts[:snapback] ? "--snapback #{opts[:snapback]}" : ''
209209

210210
source = opts[:source] || lv.origin.path
211-
$stderr.puts "Data source: #{source}" if opts[:verbose]
211+
verbose "Data source: #{source}"
212212

213213
if opts[:stdout]
214214
dump_changes(lv, source, $stdout, opts)
215215
else
216-
verbose = opts[:verbose] ? '-v' : ''
216+
verbose = $verbose ? '-v' : ''
217+
debug = $debug ? '-d' : ''
218+
217219
server_cmd = if desthost
218-
"#{opts[:rsh]} #{desthost} lvmsync --apply - #{snapback} #{verbose} #{destdev}"
220+
"#{opts[:rsh]} #{desthost} lvmsync --apply - #{snapback} #{verbose} #{debug} #{destdev}"
219221
else
220222
"#{$0} --apply - #{snapback} #{verbose} #{destdev}"
221223
end
@@ -232,7 +234,7 @@ def run_client(opts)
232234
until (active_fds = IO.select(fds, [], [], 0)).nil?
233235
active_fds[0].each do |fd|
234236
begin
235-
$stderr.puts "\e[2K\rremote:#{fd.readline}" unless opts[:quiet]
237+
info "\e[2K\rremote:#{fd.readline}"
236238
rescue EOFError, Errno::EPIPE
237239
fd.close
238240
fds.delete(fd)
@@ -251,7 +253,7 @@ def run_client(opts)
251253
until (active_fds = IO.select(fds, [], [], 0.1)).nil?
252254
active_fds[0].each do |fd|
253255
begin
254-
$stderr.puts "\e[2K\rremote:#{fd.readline}" unless opts[:quiet]
256+
info "\e[2K\rremote:#{fd.readline}"
255257
rescue EOFError, Errno::EPIPE
256258
fd.close
257259
fds.delete(fd)
@@ -262,7 +264,7 @@ def run_client(opts)
262264
end
263265

264266
if (exit_status or $?).exitstatus != 0
265-
$stderr.puts "APPLY FAILED."
267+
fatal "APPLY FAILED."
266268
end
267269
end
268270
end
@@ -282,8 +284,7 @@ def dump_changes(snapshot, source, outfd, opts)
282284
chunk_size = r.last - r.first + 1
283285
xfer_size += chunk_size
284286

285-
$stderr.puts "Sending chunk #{r.to_s}..." if opts[:verbose]
286-
$stderr.puts "Seeking to #{r.first} in #{source}" if opts[:verbose]
287+
debug "Sending chunk #{r.to_s}..."
287288

288289
origindev.seek(r.first, IO::SEEK_SET)
289290

@@ -297,7 +298,7 @@ def dump_changes(snapshot, source, outfd, opts)
297298
end
298299

299300
# Progress bar!
300-
if xfer_count % 100 == 50 and !opts[:quiet]
301+
if xfer_count % 100 == 50 and !$quiet
301302
$stderr.printf "\e[2K\rSending chunk %i of %i, %.2fMB/s",
302303
xfer_count,
303304
change_count,
@@ -311,7 +312,7 @@ def dump_changes(snapshot, source, outfd, opts)
311312
total_size = origindev.tell
312313
end
313314

314-
unless opts[:quiet]
315+
unless $quiet
315316
$stderr.printf "\rTransferred %i bytes in %.2f seconds\n",
316317
xfer_size, Time.now - start_time
317318

@@ -336,4 +337,21 @@ def parse_snapshot_name(origname)
336337
end
337338
end
338339

340+
def debug(s)
341+
$stderr.puts s if $debug
342+
end
343+
344+
def verbose(s)
345+
$stderr.puts s if $verbose or $debug
346+
end
347+
348+
def info(s)
349+
$stderr.puts s unless $quiet
350+
end
351+
352+
def fatal(s, status=1)
353+
$stderr.puts "FATAL ERROR: #{s}"
354+
exit status
355+
end
356+
339357
main

0 commit comments

Comments
 (0)