#include<stdio.h>
#include<stdlib.h>
#include<string.h>
char * ifname2pcibus(const char *ifname)
{
int i;
size_t rs;
FILE *fp = NULL;
char buf1[1024];
char buf2[1024];
char full_bus_name[1024];
// Run command
sprintf(buf1,"ethtool -i %s | grep \"bus-info:\" | sed -e \"s/bus-info: //\"", ifname);
fp = popen(buf1, "r");
if(!fp)
{
fprintf(stderr,"popen error\n");
return NULL;
}
// Read PCI bus information
rs = fread((void*)buf2, sizeof(char), 1024-1, fp);
if(!rs)
{
pclose(fp);
fprintf(stderr,"popen read error\n");
return NULL;
}
pclose(fp);
buf2[rs] = '\0';
// Remove Newline character
for ( i = 0 ; i < rs ; i++ )
{
if ( isspace(buf2[i]) )
buf2[i] = '\0';
}
return strdup(buf2);
}
int main(void)
{
char * pcibus;
pcibus = ifname2pcibus("eth0");
if(pcibus)
{
printf("eth0 : %s \n", pcibus);
free(pcibus);
}
return 0;
}
위 상태로 사용하는 것도 문제 될 만한 것은 없지만 매우 무거운 프로그램 내부에서 popen()을 하게 될 경우 내부적으로 수행되는 fork()에 의한 부담이 커지는 관계로 ioctl()을 이용한 버전을 다시 만듦.
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <net/if.h>
#include <sys/socket.h>
#include <linux/ethtool.h>
#include <linux/sockios.h>
char *ifname2pcibus(const char *ifname)
{
int fd;
struct ifreq ifr;
struct ethtool_drvinfo drvinfo;
// Open socket
fd = socket(AF_INET, SOCK_DGRAM, 0);
if(fd<0)
return NULL;
// Make Request structure
memset(&ifr, 0x00, sizeof(ifr));
strcpy(ifr.ifr_name, ifname);
drvinfo.cmd = ETHTOOL_GDRVINFO;
ifr.ifr_data = (void*)&drvinfo;
// Get Driver information
ioctl(fd, SIOCETHTOOL, &ifr);
close(fd);
return strdup(drvinfo.bus_info);
}
int main(void)
{
char * pcibus;
pcibus = ifname2pcibus("eth0");
if(pcibus)
{
printf("eth0 : %s \n", pcibus);
free(pcibus);
}
return 0;
}
#include <stdlib.h>
#include <string.h>
#include <net/if.h>
#include <sys/socket.h>
#include <linux/ethtool.h>
#include <linux/sockios.h>
char *ifname2pcibus(const char *ifname)
{
int fd;
struct ifreq ifr;
struct ethtool_drvinfo drvinfo;
// Open socket
fd = socket(AF_INET, SOCK_DGRAM, 0);
if(fd<0)
return NULL;
// Make Request structure
memset(&ifr, 0x00, sizeof(ifr));
strcpy(ifr.ifr_name, ifname);
drvinfo.cmd = ETHTOOL_GDRVINFO;
ifr.ifr_data = (void*)&drvinfo;
// Get Driver information
ioctl(fd, SIOCETHTOOL, &ifr);
close(fd);
return strdup(drvinfo.bus_info);
}
int main(void)
{
char * pcibus;
pcibus = ifname2pcibus("eth0");
if(pcibus)
{
printf("eth0 : %s \n", pcibus);
free(pcibus);
}
return 0;
}