Magellan Linux

Annotation of /trunk/openssl-c_rehash/openssl-c_rehash.sh

Parent Directory Parent Directory | Revision Log Revision Log


Revision 2875 - (hide annotations) (download) (as text)
Wed Jul 29 07:35:57 2015 UTC (8 years, 9 months ago) by niro
File MIME type: application/x-sh
File size: 4270 byte(s)
-initial import
1 niro 2875 #!/bin/sh
2     #
3     # Ben Secrest <blsecres@gmail.com>
4     #
5     # sh c_rehash script, scan all files in a directory
6     # and add symbolic links to their hash values.
7     #
8     # based on the c_rehash perl script distributed with openssl
9     #
10     # LICENSE: See OpenSSL license
11     # ^^acceptable?^^
12     #
13     # see: http://cvs.pld-linux.org/cgi-bin/viewvc.cgi/cvs/packages/openssl/openssl-c_rehash.sh?view=log
14     #
15    
16     # default certificate location
17     DIR=/etc/openssl
18    
19     # for filetype bitfield
20     IS_CERT=$(( 1 << 0 ))
21     IS_CRL=$(( 1 << 1 ))
22    
23    
24     # check to see if a file is a certificate file or a CRL file
25     # arguments:
26     # 1. the filename to be scanned
27     # returns:
28     # bitfield of file type; uses ${IS_CERT} and ${IS_CRL}
29     #
30     check_file()
31     {
32     local IS_TYPE=0
33    
34     # make IFS a newline so we can process grep output line by line
35     local OLDIFS=${IFS}
36     IFS=$( printf "\n" )
37    
38     # XXX: could be more efficient to have two 'grep -m' but is -m portable?
39     for LINE in $( grep '^-----BEGIN .*-----' ${1} )
40     do
41     if echo ${LINE} \
42     | grep -q -E '^-----BEGIN (X509 |TRUSTED )?CERTIFICATE-----'
43     then
44     IS_TYPE=$(( ${IS_TYPE} | ${IS_CERT} ))
45    
46     if [ $(( ${IS_TYPE} & ${IS_CRL} )) -ne 0 ]
47     then
48     break
49     fi
50     elif echo ${LINE} | grep -q '^-----BEGIN X509 CRL-----'
51     then
52     IS_TYPE=$(( ${IS_TYPE} | ${IS_CRL} ))
53    
54     if [ $(( ${IS_TYPE} & ${IS_CERT} )) -ne 0 ]
55     then
56     break
57     fi
58     fi
59     done
60    
61     # restore IFS
62     IFS=${OLDIFS}
63    
64     return ${IS_TYPE}
65     }
66    
67    
68     #
69     # use openssl to fingerprint a file
70     # arguments:
71     # 1. the filename to fingerprint
72     # 2. the method to use (x509, crl)
73     # returns:
74     # none
75     # assumptions:
76     # user will capture output from last stage of pipeline
77     #
78     fingerprint()
79     {
80     ${SSL_CMD} ${2} -fingerprint -noout -in ${1} | sed 's/^.*=//' | tr -d ':'
81     }
82    
83    
84     #
85     # link_hash - create links to certificate files
86     # arguments:
87     # 1. the filename to create a link for
88     # 2. the type of certificate being linked (x509, crl)
89     # returns:
90     # 0 on success, 1 otherwise
91     #
92     link_hash()
93     {
94     local FINGERPRINT=$( fingerprint ${1} ${2} )
95     local HASH=$( ${SSL_CMD} ${2} -hash -noout -in ${1} )
96     local SUFFIX=0
97     local LINKFILE=''
98     local TAG=''
99    
100     if [ ${2} = "crl" ]
101     then
102     TAG='r'
103     fi
104    
105     LINKFILE=${HASH}.${TAG}${SUFFIX}
106    
107     while [ -f ${LINKFILE} ]
108     do
109     if [ ${FINGERPRINT} = $( fingerprint ${LINKFILE} ${2} ) ]
110     then
111     echo "WARNING: Skipping duplicate file ${1}" >&2
112     return 1
113     fi
114    
115     SUFFIX=$(( ${SUFFIX} + 1 ))
116     LINKFILE=${HASH}.${TAG}${SUFFIX}
117     done
118    
119     echo "${1} => ${LINKFILE}"
120    
121     # assume any system with a POSIX shell will either support symlinks or
122     # do something to handle this gracefully
123     ln -s ${1} ${LINKFILE}
124    
125     return 0
126     }
127    
128    
129     # hash_dir create hash links in a given directory
130     hash_dir()
131     {
132     echo "Doing ${1}"
133    
134     cd ${1}
135    
136     ls -1 * 2>/dev/null | while read FILE
137     do
138     if echo ${FILE} | grep -q -E '^[[:xdigit:]]{8}\.r?[[:digit:]]+$' \
139     && [ -h "${FILE}" ]
140     then
141     rm ${FILE}
142     fi
143     done
144    
145     ls -1 *.pem 2>/dev/null | while read FILE
146     do
147     check_file ${FILE}
148     local FILE_TYPE=${?}
149     local TYPE_STR=''
150    
151     if [ $(( ${FILE_TYPE} & ${IS_CERT} )) -ne 0 ]
152     then
153     TYPE_STR='x509'
154     elif [ $(( ${FILE_TYPE} & ${IS_CRL} )) -ne 0 ]
155     then
156     TYPE_STR='crl'
157     else
158     echo "WARNING: ${FILE} does not contain a certificate or CRL: skipping" >&2
159     continue
160     fi
161    
162     link_hash ${FILE} ${TYPE_STR}
163     done
164     }
165    
166    
167     # choose the name of an ssl application
168     if [ -n "${OPENSSL}" ]
169     then
170     SSL_CMD=$(which ${OPENSSL} 2>/dev/null)
171     else
172     SSL_CMD=/usr/bin/openssl
173     OPENSSL=${SSL_CMD}
174     export OPENSSL
175     fi
176    
177     # fix paths
178     PATH=${PATH}:${DIR}/bin
179     export PATH
180    
181     # confirm existance/executability of ssl command
182     if ! [ -x ${SSL_CMD} ]
183     then
184     echo "${0}: rehashing skipped ('openssl' program not available)" >&2
185     exit 0
186     fi
187    
188     # determine which directories to process
189     old_IFS=$IFS
190     if [ ${#} -gt 0 ]
191     then
192     IFS=':'
193     DIRLIST=${*}
194     elif [ -n "${SSL_CERT_DIR}" ]
195     then
196     DIRLIST=$SSL_CERT_DIR
197     else
198     DIRLIST=${DIR}/certs
199     fi
200    
201     IFS=':'
202    
203     # process directories
204     for CERT_DIR in ${DIRLIST}
205     do
206     if [ -d ${CERT_DIR} -a -w ${CERT_DIR} ]
207     then
208     IFS=$old_IFS
209     hash_dir ${CERT_DIR}
210     IFS=':'
211     fi
212     done