Showing posts with label Shell. Show all posts
Showing posts with label Shell. Show all posts

Monday, July 4, 2022

Bash: shell script to obtain the cipher list of a server


#!/bin/bash
 
SERVER=$1
 
if [[ "$SERVER" == "" ]]; then
  echo "Usage: $0 hostname:port"
  exit
fi
 
DELAY=2
ciphers=$(openssl ciphers 'ALL:eNULL' | sed -e 's/:/ /g')
 
for cipher in ${ciphers[@]}
do
  echo -n Testing $cipher ...
  result=$(echo -n | openssl s_client -cipher "$cipher" -connect $SERVER 2>&1)
 
  if [[ "$result" =~ "Session-ID:" ]]; then
    echo "YES"
  else
    if [[ "$result" =~ ":error:" ]]; then
      error=$(echo -n $result | cut -d':' -f6)
      echo "NO \($error\)"
    elif [[ "$result" =~ "errno=104" ]]; then
      echo "NO \(Connection reset by peer\)"
    else
      echo "Unknown response"
    fi
  fi
 
  sleep $DELAY
done
 

Tuesday, May 28, 2019

Backreference in Perl vs sed


Perl uses $n (where n is a number) for backreferences; while sed uses \n.

For example, we want to switch the contents between #:# in this file:
#Hello:World#!
How #are:you#?

Using sed, we run command:
$ sed -n -e 's/#\([^:]*\):\([^#]*\)#/#\2:\1#/p' filename

Using perl, we can run command:
$ perl -p -e 's/#([^:]*):([^#]*)#/#$2:$1#/' filename

or:
$ perl -p -e 's/#([^:]*):([^#]*)#/#${2}:${1}#/' filename

The output will be:
#World:Hello#!
How #you:are#?

A few notes:
1. The backreference of sed can be only one digit. That means \10 will be \1 (the first reference) and a digit 0.
2. sed uses \( and \) to group while Perl uses ( and ) only.

Wednesday, May 1, 2019

Linux: find and replace text across multiple lines


For example, we have a file myfile.txt with the following content:

This is
my
apple
in
the basket.

We can run this command:

$ perl -0777 -i -pe 's/This is\nmy\napple/These are\nmy\napples/g' myfile.txt

to change the content of the file into:

These are
my
apples
in
the basket.

The option -0777 applies the matching to the whole file instead of line by line. The option -i makes the changes in place.

Wednesday, April 10, 2019

Linux: trim the extensions from the filenames for a batch of files


Trim the extension (e.g. .bak) of one file is simple, e.g.:

$ mv myfile01.txt.bak myfile01.txt

If we have hundreds of such files, nobody would want to run hundreds of the similar commands:

$ mv myfile02.txt.bak myfile02.txt
$ mv myfile03.txt.bak myfile03.txt
...

We can use sed instead:

$ ls *.bak | sed -e 's/\(.*\)\(\.bak\)/mv \1\2 \1/' | sh

The explanation of this command:
  1. "ls *.bak" gets the list of the filenames and feed them to sed.
  2. For each filename, sed changes it to "mv something.bak something"
  3. In the first part of the "s" command of sed, a pattern matches anything ended with .bak. It uses \( and \) to group the filename into 2 parts. The 1st group \(.*\) matches anything before .bak. The 2st group \(\.bak\) matches the exact string .bak.
  4. In the second part of the "s" command of sed (mv \1\2 \1), \1 and \2 are substituted with the 2 groups described above. So \1 refers to anything before .bak, and \2 refers to .bak.
  5. The output of sed will be "mv something.bak something" and it is passed to sh command to run.
  6. This will be done for all the files from 'ls *.bak'.
 
Get This <