~ubuntu-branches/ubuntu/natty/ruby1.8/natty-updates

« back to all changes in this revision

Viewing changes to ext/openssl/lib/openssl/x509-internal.rb

  • Committer: Package Import Robot
  • Author(s): Daigo Moriwaki
  • Date: 2010-06-27 22:16:44 UTC
  • mfrom: (22.1.12 sid)
  • Revision ID: package-import@ubuntu.com-20100627221644-7n8891uzqc17nvyq
Tags: 1.8.7.299-1
* New upstream release
* Removed patches that the upstrem has applied:
  - debian/patches/100312_timeout-fix.dpatch
  - debian/patches/100620_fix_pathname_warning.dpatch
  - debian/patches/100620_fix_super_called_outside_of_method.dpatch

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
=begin
 
2
= $RCSfile$ -- Ruby-space definitions that completes C-space funcs for X509 and subclasses
 
3
 
 
4
= Info
 
5
  'OpenSSL for Ruby 2' project
 
6
  Copyright (C) 2002  Michal Rokos <m.rokos@sh.cvut.cz>
 
7
  All rights reserved.
 
8
 
 
9
= Licence
 
10
  This program is licenced under the same licence as Ruby.
 
11
  (See the file 'LICENCE'.)
 
12
 
 
13
= Version
 
14
  $Id$
 
15
=end
 
16
 
 
17
module OpenSSL
 
18
  module X509
 
19
    class ExtensionFactory
 
20
      def create_extension(*arg)
 
21
        if arg.size > 1
 
22
          create_ext(*arg)
 
23
        else
 
24
          send("create_ext_from_"+arg[0].class.name.downcase, arg[0])
 
25
        end
 
26
      end
 
27
 
 
28
      def create_ext_from_array(ary)
 
29
        raise ExtensionError, "unexpected array form" if ary.size > 3
 
30
        create_ext(ary[0], ary[1], ary[2])
 
31
      end
 
32
 
 
33
      def create_ext_from_string(str) # "oid = critical, value"
 
34
        oid, value = str.split(/=/, 2)
 
35
        oid.strip!
 
36
        value.strip!
 
37
        create_ext(oid, value)
 
38
      end
 
39
 
 
40
      def create_ext_from_hash(hash)
 
41
        create_ext(hash["oid"], hash["value"], hash["critical"])
 
42
      end
 
43
    end
 
44
 
 
45
    class Extension
 
46
      def to_s # "oid = critical, value"
 
47
        str = self.oid
 
48
        str << " = "
 
49
        str << "critical, " if self.critical?
 
50
        str << self.value.gsub(/\n/, ", ")
 
51
      end
 
52
 
 
53
      def to_h # {"oid"=>sn|ln, "value"=>value, "critical"=>true|false}
 
54
        {"oid"=>self.oid,"value"=>self.value,"critical"=>self.critical?}
 
55
      end
 
56
 
 
57
      def to_a
 
58
        [ self.oid, self.value, self.critical? ]
 
59
      end
 
60
    end
 
61
 
 
62
    class Name
 
63
      module RFC2253DN
 
64
        Special = ',=+<>#;'
 
65
        HexChar = /[0-9a-fA-F]/
 
66
        HexPair = /#{HexChar}#{HexChar}/
 
67
        HexString = /#{HexPair}+/
 
68
        Pair = /\\(?:[#{Special}]|\\|"|#{HexPair})/
 
69
        StringChar = /[^#{Special}\\"]/
 
70
        QuoteChar = /[^\\"]/
 
71
        AttributeType = /[a-zA-Z][0-9a-zA-Z]*|[0-9]+(?:\.[0-9]+)*/
 
72
        AttributeValue = /
 
73
          (?!["#])((?:#{StringChar}|#{Pair})*)|
 
74
          \#(#{HexString})|
 
75
          "((?:#{QuoteChar}|#{Pair})*)"
 
76
        /x
 
77
        TypeAndValue = /\A(#{AttributeType})=#{AttributeValue}/
 
78
 
 
79
        module_function
 
80
 
 
81
        def expand_pair(str)
 
82
          return nil unless str
 
83
          return str.gsub(Pair){
 
84
            pair = $&
 
85
            case pair.size
 
86
            when 2 then pair[1,1]
 
87
            when 3 then Integer("0x#{pair[1,2]}").chr
 
88
            else raise OpenSSL::X509::NameError, "invalid pair: #{str}"
 
89
            end
 
90
          }
 
91
        end
 
92
 
 
93
        def expand_hexstring(str)
 
94
          return nil unless str
 
95
          der = str.gsub(HexPair){$&.to_i(16).chr }
 
96
          a1 = OpenSSL::ASN1.decode(der)
 
97
          return a1.value, a1.tag
 
98
        end
 
99
 
 
100
        def expand_value(str1, str2, str3)
 
101
          value = expand_pair(str1)
 
102
          value, tag = expand_hexstring(str2) unless value
 
103
          value = expand_pair(str3) unless value
 
104
          return value, tag
 
105
        end
 
106
 
 
107
        def scan(dn)
 
108
          str = dn
 
109
          ary = []
 
110
          while true
 
111
            if md = TypeAndValue.match(str)
 
112
              matched = md.to_s
 
113
              remain = md.post_match
 
114
              type = md[1]
 
115
              value, tag = expand_value(md[2], md[3], md[4]) rescue nil
 
116
              if value
 
117
                type_and_value = [type, value]
 
118
                type_and_value.push(tag) if tag
 
119
                ary.unshift(type_and_value)
 
120
                if remain.length > 2 && remain[0] == ?,
 
121
                  str = remain[1..-1]
 
122
                  next
 
123
                elsif remain.length > 2 && remain[0] == ?+
 
124
                  raise OpenSSL::X509::NameError,
 
125
                    "multi-valued RDN is not supported: #{dn}"
 
126
                elsif remain.empty?
 
127
                  break
 
128
                end
 
129
              end
 
130
            end
 
131
            msg_dn = dn[0, dn.length - str.length] + " =>" + str
 
132
            raise OpenSSL::X509::NameError, "malformed RDN: #{msg_dn}"
 
133
          end
 
134
          return ary
 
135
        end
 
136
      end
 
137
 
 
138
      class <<self
 
139
        def parse_rfc2253(str, template=OBJECT_TYPE_TEMPLATE)
 
140
          ary = OpenSSL::X509::Name::RFC2253DN.scan(str)
 
141
          self.new(ary, template)
 
142
        end
 
143
 
 
144
        def parse_openssl(str, template=OBJECT_TYPE_TEMPLATE)
 
145
          ary = str.scan(/\s*([^\/,]+)\s*/).collect{|i| i[0].split("=", 2) }
 
146
          self.new(ary, template)
 
147
        end
 
148
 
 
149
        alias parse parse_openssl
 
150
      end
 
151
    end
 
152
  end
 
153
end