【问题标题】:Why does this programs give segmentation fault?为什么这个程序会给出分段错误?
【发布时间】:2014-03-31 03:15:18
【问题描述】:

这是我编写的用于检查文件和磁盘之间的字节的程序。

#include <stdio.h>
#include <fcntl.h>
#include <unistd.h>

#define BYTES_TO_READ 64

int main(int argc, char **argv)
{
  int device = open("/dev/sdz", O_RDWR);
  if(device < 0)
  {
      printf("Device opening error\n");
      return 1;
  }
  int file = open("test.txt", O_RDONLY);
  if(file < 0)
  {
      printf("File opening error\n");
      return 2;
  }
  int byte, device_loc, file_loc;
  char *buff_device, *buff_file;
  for(byte = 0; byte<BYTES_TO_READ; byte++)
  {
      device_loc = lseek(device, byte, SEEK_SET); /* SEG FAULT */
      file_loc = lseek(file, byte, SEEK_SET);
      printf("File location\t%d",file_loc);
      printf("Device location\t%d",device_loc);
      read(device, buff_device, 1);
      read(file, buff_file, 1);
      if( (*buff_device) == (*buff_file) )
      {
          printf("Byte %d same", byte);
      }
      else
      {
          printf("Bytes %d differ: device\t%d\tfile\t%d\n",byte, *buff_device, *buff_file);
      }
  }
  return 0;
}

请不要问我为什么要比较 sdz 和一个文件。这正是我想做的:将文件直接写入磁盘并读回。

sdz 是一个环回设备,带有指向/dev/loop0 的链接。现在文件和磁盘是否不同并不重要,但我希望我的程序能够工作。通过一些调试,我找到了发生分段错误的位置,但我无法弄清楚原因。

长话短说:为什么这会给我分段错误?

提前致谢

【问题讨论】:

  • buff_device 看起来未初始化。
  • 我提到sdz 是一个环回设备。如果是真正的磁盘,会有什么不同吗?

标签: c segmentation-fault disk-io


【解决方案1】:

这些正在写入内存中的随机位置:

read(device, buff_device, 1);
read(file, buff_file, 1);

因为buff_device 和buff_file 是未初始化的指针。改用char 类型并传递他们的地址。

char buff_device;
char buff_file;

/* Check return value of read before using variables. */
if (1 == read(device, &buff_device, 1) &&
    1 == read(file, &buff_file, 1))
{
    if (buff_device == buff_file)
    /* snip */
}
else
{
    /* Report read failure. */
}

【讨论】:

  • 我虽然 read 会分配内存,然后将其地址放入提供给功能的缓冲区中。所以它没有,是吗?
  • @thelastblack,不,它不分配内存。
  • @thelastblack 只是一个思想实验:如果read() 确实分配了内存,那将如何影响buff_device? buff_device 是一个指针(目前指向 la la land),value 被赋予 read()。无论read() 对其值 的副本 做什么都不会影响原始buff_device。
  • @chux,正确。如果read() 要分配内存,则需要将指向指针的指针作为参数传递,以便调用者可以看到更改。
  • @chux 当我想到它时,你们是完全正确的。我不是一个 C 程序员。我主要做脚本,不涉及指针:D 感谢您的澄清
【解决方案2】:

改变:

char *buff_device, *buff_file;

到

char buff_device[1], buff_file[1];

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2021-09-22
    • 2019-04-17
    • 2017-08-16
    • 1970-01-01
    • 2018-04-12
    • 2011-09-13
    • 2017-10-14
    相关资源
    最近更新 更多