【问题标题】:Parse network 'interfaces' for read/write using pointer as parameter of functions使用指针作为函数参数解析网络“接口”以进行读/写
【发布时间】:2017-06-24 11:36:06
【问题描述】:

我写了一个小程序来读取/etc/network/interfaces,保存到*ethernet_t[],改变值,然后写回接口。在主要功能中一切正常。但是我不能将代码作为函数分离并传递数组的指针来做到这一点。以下是我的代码:

#include <stdio.h>
#include <ctype.h>

typedef struct {
  char sys_ifname[10];
  char address[20];
  char netmask[20];
  char network[20];
  char gateway[20];
  protocol_e protocol;
} ethernet_t;

#define MAX_NIC 4

char *removing_leading_and_trailing_whitespace(char *a);

int
write_to_interface (ethernet_t *interface[], const char *filename)
{
  FILE *fp;

  /* should grant root privilege */
  if ((fp = fopen(filename, "w")) == NULL) {
    perror ("fopen");
    exit (-1);
  }
  printf ("File open %s for writing successfully\n", filename);

  /* set DHCP for test */
  interface[2]->protocol = DHCP;

  fprintf (fp, "# /etc/network/interface\n");

  fprintf (fp, "\nauto lo\n");
  fprintf (fp, "iface lo inet loopback\n");

  int i;
  for (i=0; i<MAX_NIC; i++) {
    printf ("\nauto %s\n", interface[i]->sys_ifname);

    fprintf (fp, "\nauto %s\n", interface[i]->sys_ifname);
    fprintf (fp, "iface %s inet %s\n", interface[i]->sys_ifname,
            interface[i]->protocol == DHCP ? "dhcp" : "static");
    if (interface[i]->protocol == STATIC) {
        fprintf (fp, "\taddress %s\n", interface[i]->address);
        fprintf (fp, "\tnetmaks %s\n", interface[i]->netmask);
        fprintf (fp, "\tnetwork %s\n", interface[i]->network);
        fprintf (fp, "\tgateway %s\n", interface[i]->gateway);
    }
  }

  fclose(fp);
  printf ("Done!\n");
  return 0;
}

int
main(void)
{
  int i;
  char line[256];
  char *p;
  FILE *fp;
  ethernet_t interface[MAX_NIC];
  ethernet_t *current_interface = NULL;

  bzero(interface, sizeof(ethernet_t) * MAX_NIC);

#if YOCTO
  const char *filename = "/etc/network/interfaces";
#else
  const char *filename = "/etc/network/interfaces.ubuntu";
#endif

  if ((fp = fopen(filename, "r")) == NULL) {
    perror ("fopen");
    exit (-1);
  }

  i = 0;
  current_interface = interface;

  while (fgets(line, sizeof(line), fp) && i <= MAX_NIC) {
    p = removing_leading_and_trailing_whitespace(line);
    if (strlen(p) && p[0] != '#') {
        /* scan for interface name */
        if (strstr(p, "auto")) {
            p = removing_leading_and_trailing_whitespace(p + strlen("auto"));
            if (strcmp(p, "lo") != 0) { /* interface lo is loopback */
                current_interface = interface + i;
                /* interface default STATIC */
                current_interface->protocol = STATIC;
                strcpy (current_interface->sys_ifname, p);
                i++;
            }
        }
        else if (strstr(p, "dhcp") && current_interface) {
            current_interface->protocol = DHCP;
        }
        else if (strstr(p, "address") && current_interface) {
            p = removing_leading_and_trailing_whitespace(p + strlen("address"));
            memcpy (current_interface->address, p, strlen(p));
        }
        else if (strstr(p, "netmask") && current_interface) {
            p = removing_leading_and_trailing_whitespace(p + strlen("netmask"));
            memcpy (current_interface->netmask, p, strlen(p));
        }
        else if (strstr(p, "network") && current_interface) {
            p = removing_leading_and_trailing_whitespace(p + strlen("network"));
            memcpy (current_interface->network, p, strlen(p));
        }
        else if (strstr(p, "gateway") && current_interface) {
            p = removing_leading_and_trailing_whitespace(p + strlen("gateway"));
            memcpy (current_interface->gateway, p, strlen(p));
        }
    } /* if (strlen(p) && p[0] != '#') */
  } /* while */

  fclose (fp);

#if 1
  write_to_interface ((ethernet_t **)interface, filename);
#else
  /* should grant root privilege */
  if ((fp = fopen(filename, "w")) == NULL) {
    perror ("fopen");
    exit (-1);
  }
  printf ("File open %s for writing successfully\n", filename);

  interface[2].protocol = DHCP;

  fprintf (fp, "# /etc/network/interface\n");
  fprintf (fp, "# was auto generated by Vicom\n");

  fprintf (fp, "\nauto lo\n");
  fprintf (fp, "iface lo inet loopback\n");

  for (i=0; i<MAX_NIC; i++) {
    fprintf (fp, "\nauto %s\n", interface[i].sys_ifname);
    fprintf (fp, "iface %s inet %s\n", interface[i].sys_ifname,
            interface[i].protocol == DHCP ? "dhcp" : "static");
    if (interface[i].protocol == STATIC) {
        fprintf (fp, "\taddress %s\n", interface[i].address);
        fprintf (fp, "\tnetmaks %s\n", interface[i].netmask);
        fprintf (fp, "\tnetwork %s\n", interface[i].network);
        fprintf (fp, "\tgateway %s\n", interface[i].gateway);
    }
  }

  fclose(fp);
  printf ("Done!\n");
#endif

  return 0;
}

当我在 Linux 中运行它时,我得到了

File open /etc/network/interfaces.ubuntu for writing successfully Segmentation fault (core dumped)

我的问题是如何正确地取消引用函数中数组的指针?

【问题讨论】:

  • 但是interface 是结构数组,而不是结构指针数组?那么为什么你试图将它作为一个指针数组传递呢?这没有任何意义。
  • 你的函数应该只接受ethernet_t *interface 和一个大小参数。
  • 谢谢两位,我会尽快尝试的。

标签: c function pointers parameters


【解决方案1】:

谢谢some-programmer-dudeStoryTeller。 按照你的提示,我重写代码如下:

int
write_to_interface (ethernet_t *interface, const char *filename)
{
  FILE *fp;

  /* should grant root privilege */
  if ((fp = fopen(filename, "w")) == NULL) {
    perror ("fopen");
    exit (-1);
  }
  printf ("File open %s for writing successfully\n", filename);
#if 0
  (interface + 2)->protocol = DHCP;
#endif
  fprintf (fp, "# /etc/network/interface\n");
  fprintf (fp, "\nauto lo\n");
  fprintf (fp, "iface lo inet loopback\n");

  int i;
  for (i=0; i<MAX_NIC; i++) {
    fprintf (fp, "\nauto %s\n", (interface+i)->sys_ifname);
    fprintf (fp, "\nauto %s\n", (interface+i)->sys_ifname);
    fprintf (fp, "iface %s inet %s\n", (interface+i)->sys_ifname,
            (interface+i)->protocol == DHCP ? "dhcp" : "static");
    if ((interface+i)->protocol == STATIC) {
      fprintf (fp, "\taddress %s\n", (interface+i)->address);
      fprintf (fp, "\tnetmaks %s\n", (interface+i)->netmask);
      fprintf (fp, "\tnetwork %s\n", (interface+i)->network);
      fprintf (fp, "\tgateway %s\n", (interface+i)->gateway);
    }
  }

  fclose(fp);
  printf ("Done!\n");

  return 0;
}

谢谢你们!你救了我的命。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2020-10-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-11-29
    • 2011-02-04
    相关资源
    最近更新 更多