You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

gverify 2.3KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192
  1. #!/usr/bin/ruby
  2. require 'optparse'
  3. require 'yaml'
  4. require 'fileutils'
  5. require 'pathname'
  6. @options = {}
  7. def system!(cmd)
  8. system(cmd) or raise "failed to run #{cmd}"
  9. end
  10. def sanitize(str, where)
  11. raise "unsanitary string in #{where}" if (str =~ /[^\w.-]/)
  12. str
  13. end
  14. def sanitize_path(str, where)
  15. raise "unsanitary string in #{where}" if (str =~ /[^@\w\/.-]/)
  16. str
  17. end
  18. def info(str)
  19. puts str unless @options[:quiet]
  20. end
  21. ################################
  22. OptionParser.new do |opts|
  23. opts.banner = "Usage: build [options] <build-description>.yml"
  24. opts.on("-q", "--quiet", "be quiet") do |v|
  25. @options[:quiet] = v
  26. end
  27. opts.on("-r REL", "--release REL", "release name") do |v|
  28. @options[:release] = v
  29. end
  30. opts.on("-d DEST", "--destination DEST", "directory to place signature in") do |v|
  31. @options[:destination] = v
  32. end
  33. end.parse!
  34. base_dir = Pathname.new(__FILE__).expand_path.dirname.parent
  35. build_desc_file = ARGV.shift or raise "must supply YAML build description file"
  36. build_desc = YAML.load_file(build_desc_file)
  37. in_sums = []
  38. result_dir = 'result'
  39. package_name = build_desc["name"] or raise "must supply name"
  40. package_name = sanitize(package_name, "package name")
  41. destination = @options[:destination] || File.join(base_dir, "sigs", package_name)
  42. release = @options[:release] || "current"
  43. release = sanitize(release, "release")
  44. release_path = File.join(destination, release)
  45. File.exists?(release_path) or raise "#{release_path} does not exist"
  46. result_file = "#{package_name}-res.yml"
  47. #system!("gpg --detach-sign -u #{signer} -o #{release_path}/signature.pgp #{result_path}")
  48. current_manifest = nil
  49. did_fail = false
  50. Dir.foreach(release_path) do |signer_dir|
  51. next if signer_dir == "." or signer_dir == ".."
  52. signer_path = sanitize_path(File.join(release_path, signer_dir), "signer path")
  53. next if !File.directory?(signer_path)
  54. result_path = sanitize_path(File.join(signer_path, result_file), "result path")
  55. result = YAML.load_file(result_path)
  56. if !system("gpg --quiet --batch --verify #{File.join(signer_path, 'signature.pgp')} #{result_path}")
  57. puts "#{signer_dir}: BAD SIGNATURE"
  58. did_fail = true
  59. elsif current_manifest and result['out_manifest'] != current_manifest
  60. puts "#{signer_dir}: MISMATCH"
  61. did_fail = true
  62. else
  63. puts "#{signer_dir}: OK"
  64. end
  65. current_manifest = result['out_manifest']
  66. end
  67. exit 1 if did_fail