Wykrywanie bramy / routera za pomocą Bash: funkcje i zmienne

3

Piszę / wciąż burzę mózgów / bashskrypt powłoki. Którego celem jest; pomóc użytkownikowi w:

  • Interfejs z różnymi narzędziami CLI .
  • Wykonuj różne zadania administracyjne.

Może ostatecznie przekształcić się w nieco spersonalizowaną strukturę.


Szczególny wymóg, który ma:

  • Powinien on być w stanie wykryć adres IP z bramki / routera na bieżącej sieci LAN .
  • Mam wymyślić route -n |awk '/UG/{print $2}';do echo na odpowiedni adres IP na stdout .

Powinienem użyć tego wejścia jako function(){ }, że to wyjście jako $variable, lub oba ??


Oto kilka prostych pomysłów, które miałem:

  1. #function#
    gw() { route -n |awk '/UG/{print $2}'; }

  2. #variable#
    gw="$( route -n |awk '/UG/{print $2}'; )"

  3. #function#
    gw() { route -n |awk '/UG/{print $2}'; }
    
    #variable#
    gw="$( route -n |awk '/UG/{print $2}'; )"

  4. #function#
    gw() { route -n |awk '/UG/{print $2}'; }
    
    #variable#
    gw="$(gw)"

tjt263
źródło

Odpowiedzi:

2

Całkowicie odpowiedziałem na twoje pytanie, ale mam nadzieję, że jest to pomocne. Dotknąłem kilku ogólnych rzeczy, a następnie szczegółów na temat domyślnej bramy i wreszcie innych przykładów.

Oto kilka ogólnych komentarzy:

  • Sugeruję, aby utworzyć te wywołania w funkcje, które między innymi pozwolą ci zbudować swoje funkcje tak, aby funkcje wyższego poziomu mogły po prostu owijać wokół jednej lub więcej funkcji niższego poziomu.

  • Do obsługi danych wyjściowych z funkcji uważam, że użycie stdout jest najbardziej uniwersalną metodą i nadaje się do modułowego podejścia do tworzenia funkcji.

Jeśli wykonasz przypisanie zmiennych i wyeksportujesz z funkcji, problemy z zakresem spowodują problemy.

Jeśli masz funkcję, która przypisuje się do zmiennej wewnątrz tej samej funkcji; na przykład

`testFx() { export routeInfo="$(route)"; }`

Jeśli przypisanie zmiennej do routeInfo przez „testFx” ma taki sam zakres jak wywołujący - innymi słowy, jeśli funkcja jest zadeklarowana w bieżącej powłoce i wywołana z bieżącej powłoki, wynikowe przypisanie do zmiennej routeInfo będzie dostępne z tego muszla. Jeśli funkcja zostanie użyta w wykonanym skrypcie, wynik nie będzie dostępny dla powłoki, która wywołała skrypt, chociaż funkcja będzie dostępna.

Jest to trochę nadmierne uproszczenie, ale myślę, że dobrze wyjaśnia problem zakresu. Obiekty w zakresie dla rodzica są dostępne dla potomnej powłoki / procesu, ale nie odwrotnie. Trudno jest przekazać rzeczy „z powrotem” do linii (w skrócie).

Ta różnica ujawnia się w różnych zachowaniach obserwowanych podczas pozyskiwania pliku skryptu w porównaniu do wykonywania pliku skryptu.

Wykonany skrypt działa w powłoce podrzędnej / podrzędnej; plik źródłowy jest dodawany do środowiska lokalnego w bieżącym kontekście; nie w podrzędnej / podrzędnej powłoce.

Możesz przetestować to, co mówię, dodając tę ​​prostą funkcję do swojej powłoki - po prostu wklej ją (lub dodaj do .bashrc i załaduj ponownie powłokę itp.)

Następnie wywołać funkcję i spróbować echo zmiennej gospodarstwa wartości echo $routeInfo. To zadziała zgodnie z oczekiwaniami.

Wyczyść tę zmienną za pomocą unset routeInfo

Następnie utwórz prosty skrypt w następujący sposób:

vi ~/test.sh

z zawartością:

#!/bin/bash
testFx

Zapisz, zamknij i dodaj uprawnienia do wykonywania chmod +x ~/test.sh

Następnie uruchom skrypt ~/test.shz powłoki, w której jest zdefiniowana ta funkcja.

Po uruchomieniu skryptu wywołaj echo zmiennej, która powinna zawierać wartość echo $routeInfo:, a zobaczysz, że jest pusta - zakładając, że wykonałeś wywołanie unset powyżej; ponieważ eksport nie mógł przejść do nadrzędnej powłoki / procesu.

Z powodu tego problemu z zasięgiem i braku tradycyjnej wartości „return” z funkcji bash, sposób, w jaki zazwyczaj widzę wartość „wynik” z użytej funkcji bash, jest albo bezpośredni; przez pozostawienie wyjścia na standardowym wyjściu lub przechwycenie go w zmiennej. W obu przypadkach sama funkcja jest zapisywana w ten sam sposób, zmienia się tylko sposób jej wywołania.

Oto kilka przykładów „pobierania” wartości wyjściowych z funkcji bash

rslt=$(testFx)
Jeżeli można spodziewać się wiele wyników można zachować wyniki w tablicy:
rslt=($(testFx)) z ${#rslt[@]}zawierający liczbę pozycji (n), można uzyskać dostęp do elementów albo poprzez bezpośrednie indeksowania:
${rslt[$a]}z = 0 do N-1,
lub za pomocą pętli:
for i in ${rslt[@]}; do echo "$i"; done

Mam nadzieję, że to rozwiązało dużą część twojego pytania. Wrzucam kilka funkcji gromadzenia danych w sieci, które mam na moim komputerze lokalnym. Jeśli szukasz jakiejś konkretnej informacji, daj mi znać, prawdopodobnie mam do tego funkcję.

getExternalIP () {
    lynx -dump -hiddenlinks=ignore -nolist http://checkip.dyndns.org:8245/ | grep "Current IP Address" | cut -d":" -f2 | cut -d" " -f2
}

getLanIP () {
    ip addr show | grep -E -v '127\.0' | grep -Eo '^.*brd' | grep -Eo '[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}'
}

getDefGW_IP () { 
    route -n | awk '/UG/ {print $2}'; 
}

getDefGW_Host () { 
    route  | awk '/default/ {print $2}'; 
}    

getDefGW_Host_and_IP () { 
    echo "Def. GW hostname / IP Address: $(getDefGW_Host) / $(getDefGW_IP)";
}

Oto przydatny ciąg wyrażeń regularnych do użycia podczas pracy z adresami IP:

iprgx='(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)'

Przykład użycia tej funkcji - funkcja wyświetlająca wszystkie adresy IP w twojej sieci LAN, z których widziałeś pakiety ARP:

getARPTable_IPs() {
    arp -na | grep -Eo "$iprgx";
}

Przechowuj wyniki w tablicy:

arpIPs=($(getARPTable_IPs))

Na koniec, dla nowoczesnej dystrybucji Linuksa, oto polecenia i lokalizacje systemu plików, których często używam, aby uzyskać informacje / status sieci. Starsze polecenia, takie jak netstat i ifconfig, są przestarzałe i nie bez powodu.

  1. ip
  2. ss
  3. W katalogu / sys / class / net będzie katalog dla każdej karty sieciowej w systemie wypełniony plikami zawierającymi informacje o sieci.
    za. Wiele narzędzi wiersza poleceń po prostu korzysta z tych danych wyjściowych i ponownie je formatuje.
    b. / proc / net ma wiele informacji.
    do. Na przykład arp -napolecenie może być całkowicie zreplikowane przezcat /proc/net/arp
  4. iptables
Argonauci
źródło
Więcej informacji; lepiej. Dzięki za wkład, przeczytam go w całości nieco później. Bardzo mile widziane.
tjt263