相关疑难解决方法(0)

fork(),vfork(),exec()和clone()之间的区别

我希望在Google上找到这四者之间的差异,我希望有关于此的大量信息,但四个电话之间确实没有任何可靠的比较.

我开始尝试编译一种基本的一目了然的看看这些系统调用之间的差异,这就是我得到的.所有这些信息是否正确/我错过了什么重要的事情?

Fork :fork调用基本上复制了当前进程,几乎在所有方面都是相同的(并非所有内容都被复制,例如,某些实现中的资源限制,但想法是尽可能创建尽可能接近的副本).

新进程(子进程)获取不同的进程ID(PID),并将旧进程(父进程)的PID作为其父PID(PPID).因为这两个进程现在运行的代码完全相同,所以它们可以通过fork的返回代码告诉哪个进程 - 子进程为0,父进程获取子进程的PID.当然,这就是假设fork调用有效 - 如果没有,则不创建子节点并且父节点获取错误代码.

Vfork:vfork和fork之间的基本区别在于,当使用vfork()创建新进程时,父进程将暂时挂起,子进程可能会借用父进程的地址空间.这种奇怪的状态一直持续到子进程退出或调用execve(),此时父进程继续.

这意味着vfork()的子进程必须小心,以避免意外修改父进程的变量.特别是,子进程不能从包含vfork()调用的函数返回,并且它不能调用exit()(如果需要退出,它应该使用_exit();实际上,对于子进程也是如此正常的fork()).

Exec :exec调用是一种基本上用新程序替换整个当前进程的方法.它将程序加载到当前进程空间并从入口点运行它.exec()用函数指向的可执行文件替换当前进程.除非存在exec()错误,否则控件永远不会返回到原始程序.

Clone :克隆,作为fork,创建一个新进程.与fork不同,这些调用允许子进程与调用进程共享其执行上下文的一部分,例如内存空间,文件描述符表和信号处理程序表.

使用clone创建子进程时,它将执行函数应用程序fn(arg).(这与fork不同,fork从原始fork调用开始继续执行.)fn参数是指向子进程在执行开始时调用的函数的指针.arg参数传递给fn函数.

当fn(arg)函数应用程序返回时,子进程终止.fn返回的整数是子进程的退出代码.子进程也可以通过调用exit(2)或在收到致命信号后明确终止.

获得的信息形式:

感谢您抽时间阅读 !:)

linux fork clone process exec

190
推荐指数
4
解决办法
14万
查看次数

如何在C++代码/项目中查找内存泄漏?

我是Windows平台上的C++程序员.我正在使用Visual Studio 2008.

我通常在内存泄漏的代码中结束.

通常我通过检查代码发现内存泄漏,但它很麻烦,并不总是一个好方法.

由于我买不起付费内存泄漏检测工具,我希望你们建议尽可能避免内存泄漏的方法.

  1. 我想知道程序员如何找到内存泄漏.
  2. 是否有任何标准或程序应该遵循以确保程序中没有内存泄漏?

c++ memory-leaks

157
推荐指数
12
解决办法
21万
查看次数

如何用gdb分析程序的核心转储文件?

我的程序运行如下:

exe -p param1 -i param2 -o param3
Run Code Online (Sandbox Code Playgroud)

它崩溃并生成了一个核心转储文件 core.pid

我想通过分析核心转储文件

gdb ./exe -p param1 -i param2 -o param3 core.pid
Run Code Online (Sandbox Code Playgroud)

但是gdb认识到core.pidgdb输入的参数.

在这种情况下如何分析核心转储文件?

linux debugging gdb coredump

140
推荐指数
6
解决办法
42万
查看次数

如何转到GDB的上一行?

是否有可能在gdb中转到当前执行行之前的一行.例如:


void my_fun( somePtrType** arr,int start,int end)
{
 // arr is an array of pointers to somePtrType
  //line a
 ... some assignments
 swap(&arr[ind1] , &arr[ind2] ) ;
 //line b (current line )
}
Run Code Online (Sandbox Code Playgroud)

我现在在b行,可以检查arr那里的值,但我想回到第一行并检查arr那时的内容.

我认为这可能是不可能的,因为调试器可以以慢动作运行代码,但不能使其向后执行.
更多见解..

debugging gdb

65
推荐指数
5
解决办法
6万
查看次数

alloca() 在内存级别如何工作?

我试图弄清楚alloca()在记忆层面上实际上是如何工作的。来自Linux 手册页

alloca() 函数在调用者的堆栈帧中分配 size 字节的空间。当调用 alloca() 的函数返回到其调用者时,该临时空间会自动释放。

这是否意味着将按字节alloca()转发堆栈指针n?或者说新创建的内存到底分配在哪里?

这不是与可变长度数组完全相同吗?

我知道实现细节可能留给操作系统之类的东西。但我想知道一般来说这是如何实现的。

c alloca stack-frame variable-length-array

45
推荐指数
3
解决办法
4193
查看次数

为什么这个内存地址%fs:0x28(fs [0x28])有一个随机值?

我写了一段C代码,我已经拆解了它,并阅读了寄存器以了解程序在汇编中的工作原理.

int test(char *this){
    char sum_buf[6];
    strncpy(sum_buf,this,32);
    return 0;
}
Run Code Online (Sandbox Code Playgroud)

我一直在研究的代码是测试功能.当我反汇编输出我的测试功能时,我得到...

   0x00000000004005c0 <+12>:        mov    %fs:0x28,%rax
=> 0x00000000004005c9 <+21>:        mov    %rax,-0x8(%rbp)
... stuff ..
   0x00000000004005f0 <+60>:        xor    %fs:0x28,%rdx
   0x00000000004005f9 <+69>:        je     0x400600 <test+76>
   0x00000000004005fb <+71>:        callq  0x4004a0 <__stack_chk_fail@plt>
   0x0000000000400600 <+76>:        leaveq 
   0x0000000000400601 <+77>:        retq 
Run Code Online (Sandbox Code Playgroud)

我想知道的mov %fs:0x28,%rax是真正在做什么?

c gcc x86-64 buffer-overflow disassembly

25
推荐指数
1
解决办法
1万
查看次数

从 Python 调用 C:传递 numpy 指针列表

我有可变数量的 numpy 数组,我想将其传递给 C 函数。我设法传递了每个单独的数组(使用<ndarray>.ctypes.data_as(c_void_p)),但数组的数量可能会有很大差异。

我以为我可以在列表中传递所有这些“指针”并PyList_GetItem()在 C 代码中使用该函数。它就像一个魅力,除了所有元素的值不是我通常在作为函数参数传递时得到的指针。

不过,如果我有:

from numpy import array
from ctypes import py_object

a1 = array([1., 2., 3.8])
a2 = array([222.3, 33.5])

values = [a1, a2]

my_cfunc(py_object(values), c_long(len(values)))
Run Code Online (Sandbox Code Playgroud)

我的 C 代码看起来像:

void my_cfunc(PyObject *values)
{
    int i, n;

    n = PyObject_Length(values)
    for(i = 0; i < n; i++)
    {
        unsigned long long *pointer;
        pointer = (unsigned long long *)(PyList_GetItem(values, i);
        printf("value 0 : %f\n", *pointer);
    }
}
Run Code Online (Sandbox Code Playgroud)

打印值都是0.0000

我尝试了很多不同的解决方案,使用ctypes.byref()ctypes.pointer() …

python numpy list void-pointers multidimensional-array

6
推荐指数
1
解决办法
1754
查看次数

什么是堆栈粉碎(C)?

码:

int str_join(char *a,  const char *b) {
   int sz =0; 
   while(*a++) sz++;  
   char *st = a -1, c;  
   *st = (char) 32;
   while((c = *b++)) *++st = c;  
   *++st = 0;
   return sz;
}

....

char a[] = "StringA"; 
printf("string-1 length = %d, String a = %s\n", str_join(&a[0],"StringB"), a);
Run Code Online (Sandbox Code Playgroud)

输出:

string-1 length = 7,char*a = StringA StringB

***堆栈粉碎检测****:/ T02终止

中止(核心倾倒)

我不明白为什么它会显示堆栈粉碎?什么是*堆栈粉碎?或者是我编译器的错误?

c stack-overflow gcc stack-smash

5
推荐指数
2
解决办法
2万
查看次数

检测到段故障和堆栈粉碎之间的差异

我遇到过两种错误,一种是分段错误,另一种是Stack smashing检测到.我想知道它们之间有什么不同以及造成它们的不同原因.

c

4
推荐指数
2
解决办法
1344
查看次数

Valgrind错过了错误

(原帖在这里)

考虑以下明显的错误计划:

#include <string.h>

int main()
{
  char string1[10] = "123456789";
  char *string2 = "123456789";

  strcat(string1, string2);
}
Run Code Online (Sandbox Code Playgroud)

并假设编译它:

gcc program.c -ggdb
Run Code Online (Sandbox Code Playgroud)

并在其上运行valgrind:

valgrind --track-origins=yes --leak-check=yes --tool=memcheck --read-var-info=yes  ./a.out
Run Code Online (Sandbox Code Playgroud)

在结果中,没有显示错误:

==29739== Memcheck, a memory error detector
==29739== Copyright (C) 2002-2011, and GNU GPL'd, by Julian Seward et al.
==29739== Using Valgrind-3.7.0 and LibVEX; rerun with -h for copyright info
==29739== Command: ./a.out
==29739== 
==29739== 
==29739== HEAP SUMMARY:
==29739==     in use at exit: 0 bytes in 0 blocks
==29739== …
Run Code Online (Sandbox Code Playgroud)

c valgrind

4
推荐指数
1
解决办法
566
查看次数