sed hash in multiple lines

Hi everybody,

I am writing a little script to manage keystores and need some help with sed.

The output of the keystore file is like:

vi 2, Dec 7, 2012, trustedCertEntry,
Certificate fingerprint (MD5): F9:1F:FE:E6:A3:CB:99:88:44:D4:67:ED:G5:F8:97:7A
system@remote-server, Dec 17, 2013, PrivateKeyEntry,
Certificate fingerprint (MD5): 2A:DD:4B:C5:AD:B0:MF:96:51:B0:14:4A:B5:6C:99:FB
verisign intermediate 1, Dec 7, 2012, trustedCertEntry,
Certificate fingerprint (MD5): 4E:F6:A0:FC:40:0C:AE:9C:05:2F:AE:99:C6:7D:37:9F

So what I want, is the hash sum of "system@remote-server" (e.g. 2A:DD:4B:C5:AD:B0:MF:96:51:B0:14:4A:B5:6C:99:FB )

What I tried as far is:

sed -e "system@remote-server.*PrivateKeyEntry,/,/Certificate fingerprint.*:[a-zA-Z0-9]{2}$/ {/\([[a-zA-Z0-9]{2}[:]]*[a-zA-Z0-9]{2}$\)/\1/p}"

and

sed -n "s/system@remote-server.*PrivateKeyEntry.*Certificate fingerprint:*([a-zA-Z0-9_-]): \([[a-zA-Z0-9]{2}[:]]*[a-zA-Z0-9]{2}$\)/\1/p"

but I don't get any output for them.

ps: the easy way would be grep -A 1 "system@remote-server.*PrivateKeyEntry" | tail -1 | cut -f 4 -d " " , but it is not reliable. Therefore I want to do it with sed.

Does anybody have a solution for me?

Thank you all in advance and regards
Hamss

Hello,

Could you please use the following code for same.

awk '/system@remote-server, Dec 17, 2013, PrivateKeyEntry,/ {getline; print $0}' file_name | sed 's/Certificate fingerprint (MD5): //g'

Output will be as folllows.

2A:DD:4B:C5:AD:B0:MF:96:51:B0:14:4A:B5:6C:99:FB

Thanks,
R. Singh

1 Like

Hi,
In sed:

sed -n -e '/system@remote-server.*PrivateKeyEntry/,/Certificate fingerprint/{/system@remote-server.*PrivateKeyEntry/d;s/.* \([0-9A-F]\+:\)/\1/p;}' 

Simplified:

sed -n -e '/system@remote-server.*PrivateKeyEntry/,/Certificate fingerprint/{/Certificate fingerprint/s/.* \([0-9A-F]\+:\)/\1/p;}' 

Because "d" command is not need with "-n" option...(why delete line that we won't print ?)
Regards.

1 Like
sed -n '/system@remote-server/{n;s/.* //p}' file

2A:DD:4B:C5:AD:B0:MF:96:51:B0:14:4A:B5:6C:99:FB
1 Like

I'm not sure that this solution is possible otherwise the solution will also be possible with grep...

This actually does not work in my case...

Thank you all for the suggestions. I need to play a bit around with them.

General question; Is it possible to merge multiple regex into one?

E.g. for this case.
We have a this hash and want to make a regex ohny for this pattern 2A:DD:4B:C5:AD:B0:MF:96:51:B0:14:4A:B5:6C:99:FB

So I am increasing the patterns, and merging one into an other:

  1. pattern: ([A-Z0-1][A-Z0-1]:) set pattern
  2. pattern: ([[A-Z0-1][A-Z0-1]:]*) pattern 1 0-infinite times
  3. pattern: ([[A-Z0-1][A-Z0-1]:]*[A-Z0-1][A-Z0-1]) and put the last two chars at the end

Is this possible?

---------- Post updated at 07:19 PM ---------- Previous update was at 06:05 PM ----------

Thanks this works good in my case. But I would like to pattern the hash itself. How would you do that?

$ cat file
vi 2, Dec 7, 2012, trustedCertEntry,
Certificate fingerprint (MD5): F9:1F:FE:E6:A3:CB:99:88:44:D4:67:ED:G5:F8:97:7A
system@remote-server, Dec 17, 2013, PrivateKeyEntry,
Certificate fingerprint (MD5): 2A:DD:4B:C5:AD:B0:MF:96:51:B0:14:4A:B5:6C:99:FB
verisign intermediate 1, Dec 7, 2012, trustedCertEntry,
Certificate fingerprint (MD5): 4E:F6:A0:FC:40:0C:AE:9C:05:2F:AE:99:C6:7D:37:9F
$ awk '/system@remote-server/ && getline && gsub(/.*\): /,x)' file

2A:DD:4B:C5:AD:B0:MF:96:51:B0:14:4A:B5:6C:99:FB
1 Like

Some more:

awk 'f{print $NF; f=0} /system@remote-server/{f=1}' file
sed '/system@remote-server/!d;N;s/.* //' file
2 Likes

Hello Scrutinizer,

Thanks a lot for nice code. Could you please explain the code please.

Thanks,
R. Singh

Sure:

awk '
  f{                         # if f=1 then (if a match was found previously)
    print $NF                # print the last field
    f=0                      # reset f ( set found is false)
  } 
  /system@remote-server/{    # if a match is found
    f=1                      # then set f to 1
  }
' file
sed '
  /system@remote-server/!d   # if a match is found then do not delete the line
  N                          # append the next line to the current line
  s/.* //                    # delete everything unto and including the last space
' file
1 Like

In your hash, I doubt you have :MF:
In general, it's a serie of hex digit.
Your pattern 2 is not pattern 1 0-infinite times, you can simplified your pattern 2 as: ([A-Z0-1:]*)
If you want pattern 1 0-infinite, you can do as: (([A-Z0-1][A-Z0-1]:)*)
And so, pattern 3: (([A-Z0-1][A-Z0-1]:)*[A-Z0-1][A-Z0-1])

And if you want that your pattern is a regex for your hash, the pattern 3 will:
(([0-9A-F][0-9A-F]:)*[0-9A-F][0-9A-F])

Regards.

1 Like

Thank you Scrutinizer for explaination. Here is one more approach for same.

$ awk '/system@remote-server, Dec 17, 2013, PrivateKeyEntry,/ {getline; gsub(/Certificate fingerprint/, "");print$NF}' file_name
2A:DD:4B:C5:AD:B0:MF:96:51:B0:14:4A:B5:6C:99:FB

Thanks,
R. Singh

1 Like

If you want the regex to match the fingerprint, try:

sed -rn 's/.*(([A-F0-9]{2}:){15}[A-F0-9]{2})/\1/p' file

This does not necessarily work with all sed versions, and, as pointed out before, it matches HEX numbers only - if you really have sth. like MF in there, adapt the ranges.

1 Like

Thanks a lot, that was what I wanted to know :b:

---------- Post updated at 01:44 PM ---------- Previous update was at 01:39 PM ----------

Thats actually true. I've changed some digs before posting. :slight_smile: