I'm writting a litlle bash script for debian. I want to find the 3th octet of my IPv4 and push it into "ip1" variable, and push the final octet in "ip2" variable. After some researches I found a script which is supposed to give me the first octet but i do not uderstant this part :

'(?<=inet )[^.]+' 

Some one could explain this to me and how can I adapt this to my needs.

I read this https://explainshell.com/... so I know how works -oP but still don't understand the last part.

ip1=$(ip a show | grep -oP '(?<=inet )[^.]+')
ip2=$(ip a show | grep -oP '(?<=inet )[^.]+')

-P means that grep should use the Perl regexp syntax and in Perl, (?<=pattern) is a "zero-width positive look-behind assertion", in other words, an anchor that should appear before the match itself. So (?<=inet )[^.]+ matches a non-empty sequence of characters that aren't periods ([^.]+), if they follow "inet ", in other words the first byte of the various IP addresses of your network interfaces because ip address show output lines such as inet scope host lo.

This is done that way because the -o options of grep makes it output the match and you don't want the "inet " bit to be printed even if it is important to the match.

The question is what can you do with just the first byte of your various IP addresses, and why ip2 is set to the same value as ip1. What is the script for?

For your specific needs, something like:

# get last two bytes of IP (assume in 192.168.*. network)
last_two=$(ip a show | grep -oP '(?<=inet 192\.168\.)[^/]+')
# Split result in two
IFS=. read net host <<< $last_two
  • Here i just put the code like i found without modifications i want ip1=3th byte and ip2=4th byte of my ip. This is for make uniques hostname for my local network computers with ip1=room and ip2=computer. – Adrien Apr 17 at 21:08
  • Ok thank you it's very clear for the (? <= Pattern) part. For me ip a gives something like inet 192.168.x.x / 24 brd 192.168.x.254 .... . So if I understand correctly, to find just the third part of my IPv4 address I should make a command like: ip1=$(ip a show | grep -oP '(?<=inet 192.168.)[^.]+') But how to do for the last part ? – Adrien Apr 17 at 21:38
  • Why do you want your address in parts? ip a show | grep -oP '(?<=inet )[^/]+' will extract the whole address. – xenoid Apr 17 at 22:56
  • I want 2 variable for my little script to adress a unique hostname to a computeur based on : 192.168.x.y the x number will determine the first part of the host name based on the room name where are the computers (I have several room with differents local network e.g. for Office; for playroom; ...). And the y number will give the second part of hostname -1 ; -2 ; -3 .... This will give hostname like Office-1 ; Office-2 ; Office-3 ; Play-1 ; Play-2 ; Store-1 ; Store-2 ; Store-3... So I need th ip adresse in part =) – Adrien Apr 18 at 10:53
  • So Maybe this could work ? : ip1=$(ip a show | grep -oP '(?<=inet 192.168)[^.]+') ip2=$(ip a show | grep -oP '(?<=inet 192.168)[^/]+') | grep -oP '(?<=.)[^ ]+') I'm not sure for the second line : i want in the second grep select all after the point but i think this is not the good syntax – Adrien Apr 18 at 11:03

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.