race_check_and_mem_leak_on_cpp
问题代码
v1_race 版本
test_race_and_leak.cpp
#include <pthread.h>
#include <iostream>
static int a;
void *_work_1(void *args)
{
for (int i = 0; i < 1000; i++)
{
a += 1;
}
int *x = new int;
return 0;
}
int main(int argc, char *argv[])
{
a = 0;
int count = 1000;
pthread_t cThreads[count];
for (int i = 0; i < count; i++)
{
pthread_create(&cThreads[i], NULL, _work_1, NULL);
}
for (int i = 0; i < count; i++)
{
pthread_join(cThreads[i], NULL);
}
std::cout << " a : " << a << std::endl;
return 0;
}
build code
g++ -o test_race_and_leak test_race_and_leak.cpp -lpthread
# 正确结果 应该是
1000000
# 多次 运行 结果 都小于 1000000
# 说明出现了 data race 数据 争抢 以及 脏读
./test_race_and_leak
a : 999700
race 数据 竞争 分析
https://stackoverflow.com/questions/5360491/how-i-can-detect-memory-leaks-of-c-application-in-linux-ubuntu-os
https://valgrind.org/
检查后 提示 出现了 数据争抢 发生在
0x10C158 同时被 线程 2 线程 3 写入 4 bytes, 也就是 一个 整形的大小
apt install valgrind -y
valgrind --tool=memcheck <your_app> <your_apps_params>
valgrind --tool=memcheck test_race_and_leak
./test_race_and_leak
a : 999779
# 数据 竞争 检查
valgrind --tool=helgrind ./test_race_and_leak
# ==2592589== Possible data race during write of size 4 at 0x10C158 by thread #3
# ==2592589== Locks held: none
# ==2592589== at 0x10924E: _work_1(void*) (in /root/learn_threads/test_race_and_leak)
# ==2592589== by 0x4842B1A: ??? (in /usr/lib/x86_64-linux-gnu/valgrind/vgpreload_helgrind-amd64-linux.so)
# ==2592589== by 0x4865608: start_thread (pthread_create.c:477)
# ==2592589== by 0x4B83292: clone (clone.S:95)
# ==2592589==
# ==2592589== This conflicts with a previous write of size 4 by thread #2
# ==2592589== Locks held: none
# ==2592589== at 0x10924E: _work_1(void*) (in /root/learn_threads/test_race_and_leak)
# ==2592589== by 0x4842B1A: ??? (in /usr/lib/x86_64-linux-gnu/valgrind/vgpreload_helgrind-amd64-linux.so)
# ==2592589== by 0x4865608: start_thread (pthread_create.c:477)
# ==2592589== by 0x4B83292: clone (clone.S:95)
# ==2592589== Address 0x10c158 is 0 bytes inside data symbol "_ZL1a"
# ==2592589==
# a : 1000000
# ==2592589==
# ==2592589== Use --history-level=approx or =none to gain increased speed, at
# ==2592589== the cost of reduced accuracy of conflicting-access information
# ==2592589== For lists of detected and suppressed errors, rerun with: -s
# ==2592589== ERROR SUMMARY: 1998 errors from 2 contexts (suppressed: 0 from 0)
内存泄露检查
检查后 提示 出现了 内存 泄露 发生在
malloc (in /usr/lib/x86_64-linux-gnu/valgrind/vgpreload_memcheck-amd64-linux.so)
by 0x10942E: main (in /root/learn_threads/test_race_and_leak)
# 内存 泄露检查
valgrind --tool=memcheck --leak-check=full -s ./test_race_and_leak
# ==2599297== HEAP SUMMARY:
# ==2599297== in use at exit: 100 bytes in 1 blocks
# ==2599297== total heap usage: 1,003 allocs, 1,002 frees, 361,828 bytes allocated
# ==2599297==
# ==2599297== 100 bytes in 1 blocks are definitely lost in loss record 1 of 1
# ==2599297== at 0x483B7F3: malloc (in /usr/lib/x86_64-linux-gnu/valgrind/vgpreload_memcheck-amd64-linux.so)
# ==2599297== by 0x10942E: main (in /root/learn_threads/test_race_and_leak)
# ==2599297==
# ==2599297== LEAK SUMMARY:
# ==2599297== definitely lost: 100 bytes in 1 blocks
# ==2599297== indirectly lost: 0 bytes in 0 blocks
# ==2599297== possibly lost: 0 bytes in 0 blocks
# ==2599297== still reachable: 0 bytes in 0 blocks
# ==2599297== suppressed: 0 bytes in 0 blocks
# ==2599297==
# ==2599297== For lists of detected and suppressed errors, rerun with: -s
# ==2599297== ERROR SUMMARY: 1 errors from 1 contexts (suppressed: 0 from 0)