Como o ifconfg busca os NICs habilitados?

1

Eu pesquisei isso há algum tempo, mas não havia palavras-chave claras para encontrar a mesma pergunta.

Mostrando brevemente minha pergunta:

ifconfig mostra apenas as NICs ativadas.

# ifconfig
br0       Link encap:Ethernet  HWaddr XX:XX:XX:XX:XX:XX
          UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1
          ...

eth0      Link encap:Ethernet  HWaddr XX:XX:XX:XX:XX:XX
          inet addr:XX.XX.XX.XX  Bcast:XX.XX.XX.XX  Mask:XX.XX.XX.XX
          UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1
          ...

lo        Link encap:Local Loopback  
          inet addr:127.0.0.1  Mask:255.0.0.0
          UP LOOPBACK RUNNING  MTU:16436  Metric:1
          ...

No entanto, ip addr mostra todas as NICs.

# ip addr
1: lo: <LOOPBACK,UP,LOWER_UP> ... UNKNOWN 
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> ... state UP
3: eth1: <BROADCAST,MULTICAST> ... state DOWN
8: br0: <BROADCAST,MULTICAST,UP,LOWER_UP> ... state UNKNOWN

Com base na saída de tela, eu sabia que ifconfig sabe se as NICs estão ativadas ou não via string UP . (por exemplo, LOOPBACK, UP , LOWER_UP)

Até onde eu sei, essa string não depende do hardware. Assim, nem /sys/class/net/NIC/operstate nem /sys/class/net/NIC/carrier é a resposta.

Minha pergunta é: de onde vem essa string?

(Eu acho que está contido em algum arquivo do sistema de arquivos.)

    
por Kir Chou 15.06.2016 / 08:36

2 respostas

2

man ifconfig diz:

O ifconfig é usado para configurar as interfaces de rede residentes no kernel. Ele é usado no momento da inicialização para configurar interfaces conforme necessário. Depois disso, geralmente é necessário apenas quando depuração ou quando o ajuste do sistema é necessário.

If no arguments are given, ifconfig displays the status of the currently active interfaces.

Se um único argumento de interface for fornecido, ele exibirá o status da interface especificada apenas;

if a single -a argument is given, it displays the status of all interfaces, even those that are down.

Caso contrário, configura uma interface.

man netdevice também pode compartilhar alguma luz sobre a questão. Usa a chamada do sistema ioctl ().

Outra técnica é usar strace .

Ele fornece uma lista de todas as chamadas do sistema feitas por qualquer programa que você passe, junto com seus argumentos e valores de retorno. Se o seu programa apenas descarregar alguma informação e terminar em vez de ser executado por um longo período de tempo, pode ser bastante simples fazer apenas um homem em todas as chamadas do sistema que você vê que parecem fornecer as informações que você está procurando.

Quando eu corro

strace ifconfig

Algumas das chamadas interessantes são:

open("/proc/net/dev", O_RDONLY)         = 6

seguido por um monte de ioctls:

ioctl(5, SIOCGIFFLAGS, {ifr_name="eth0", ifr_flags=IFF_UP|IFF_BROADCAST|IFF_RUNNING|IFF_MULTICAST}) = 0
ioctl(5, SIOCGIFHWADDR, {ifr_name="eth0", ifr_hwaddr=12:cd:4b:bb:7f:39}) = 0
ioctl(5, SIOCGIFMETRIC, {ifr_name="eth0", ifr_metric=0}) = 0
ioctl(5, SIOCGIFMTU, {ifr_name="eth0", ifr_mtu=9001}) = 0
    
por 15.06.2016 / 09:05
0

Obrigado pela ajuda de Miley. Aqui está o meu código de teste.

check_ifup.c

#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <sys/socket.h>
#include <sys/ioctl.h>
#include <net/if.h>

int main(int argc, char* argv[])
{
    if (argc < 2)
    {   
        printf("Usage: ./check_ifup interface_name\n");
        return 0;
    }   

    struct ifreq ifr;
    int sockfd;

    sockfd = socket(AF_INET, SOCK_DGRAM, 0); 
    bzero(&ifr, sizeof(ifr));
    strcpy(ifr.ifr_name, argv[1]);
    ioctl(sockfd, SIOCGIFFLAGS, &ifr);

    if (ifr.ifr_flags & IFF_UP)    
        printf("%s is up\n", argv[1]);
    else
        printf("%s is down or unknown\n", argv[1]);                                                            

    close(sockfd);
    return 0
}

Referência:

  1. Definição de sinalizadores de interface
  2. ifconfig.c
  3. Alguns tutoriais (em chinês)
  4. Diferença entre IFF_UP e IFF_RUNNING
por 15.06.2016 / 09:57