有时,dba遇到段错误而执行一些查询问题。然而,这是一个最新的话题。我试着在互联网上搜索细节相关的段错误,发现很多文章;然而,它没能解渴,可他们都没有我正在寻找的答案。所以,我决定收集信息,写一份详细的关于这个问题的博客。
为了理解“段错误”,要知道细分的基本思想及其在C编程实现。在这个博客中,我还将覆盖场景导致段错误”。
基本的了解
为了理解段错误,有必要理解内存管理方法流程。
当我们需要执行任何程序时,应该是先加载到内存中。记忆里,他们可以分配任何可用的空间。当一个程序离开了记忆,空间可用;然而,操作系统可能无法空内存空间分配给另一个程序或过程,它有一些问题。新项目所需的空间的可能高于可用的空间碎片,程序应该分为不同的块加载到内存中之前,由于内存管理具有挑战性的,因为它会导致分裂。
为了克服这些问题,介绍了分页和分段的概念,物理地址空间和虚拟地址空间的设计。这些概念的详细描述如下。
分页
这是为了允许不连续的空间分配过程。这里,内存被分成相同大小的分区程序的代码驻留的地方。在主内存块被称为帧,当他们被称为在二级页面(或硬盘驱动器)。为了处理内存管理,一个叫做内存管理单元(MMU)结构,内存块分为主要部分:逻辑地址空间和物理地址空间。
逻辑地址空间:它包含逻辑地址生成程序的CPU。
物理地址空间:它有物理地址指针指向内存中的实际位置。
为了执行实际的翻译逻辑地址到物理地址的MMU需要执行内存映射操作,可以通过另一个结构称为页表。一个页表实际引用为逻辑地址相关的物理地址。
下图描述了相同的。

分割
这个方案被介绍给克服分页的缺点;不过,它的工作原理类似于分页。而不是固定大小的页,创建不同大小的片段,是基于程序代码。在这种情况下,我们不需要物理地址空间。在这里,一个段表管理一切。
在这里,虚拟地址到物理地址的转换(逻辑)和段表存储足够的信息更容易。
我不会进一步深入这个话题,因为它需要更多的技术的理解。增加这部分的目的是有一个基本的了解逻辑地址到物理地址的映射。

段错误是什么?
如上所述,CPU首先获取一个逻辑地址,并通过使用一个页表或一段表,它发现/计算所需内存的物理地址的位置。内存管理是如何工作的。
为了访问所需的位置,我们有时会遇到一些问题,如下所述。
- 偶尔,在计算物理地址使用页面/段表,程序遇到问题需要内容(代码、变量或其他)在物理内存位置不可用。这种现象被称为“页面错误”。这不是不寻常的和不影响执行的过程中只是在内存中加载的项目。
- 另一个是一个经典的案例无法访问的内存位置。当生成的物理地址指向一个物理位置无法访问的程序。这就是所谓的“段错误”,终止流程执行。这是当一个程序试图访问一个只读内存或另一个程序的一部分空间。
虽然段错误被诽谤是致命的,它仍然是强制性的,因为它是一种机制提供保护,以防止任何内部腐败。
注意:段错误分割的内存管理方法无关。
可再生的场景
而探索在代码级别,有很多场景导致段错误,如缓冲区溢出、堆栈溢出,等等。然而,这个博客写从数据库角度;因此,我不喜欢深入这些场景是非常高级的编程概念。
在这一节中,我将集中在一个场景在PostgreSQL数据库导致段错误。
这是我遇到一次数据库重新启动因“段错误。“下面是一行代码,导致段错误在PostgreSQL 13.4和12.8。
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20.
21
22
23
24
25
26
27
|
创建
模式
调试
;
创建
表
调试
。
downloaded_images
(
itemid
文本
不
零
,
download_time
时间戳
,
主
关键
(
itemId
)
)
;
插入
成
调试
。
downloaded_images
(
itemid
,
download_time
)
值
(
“1190300”
,
“2021-09-07 11:00:10.255831”
)
;
开始
;
创建
表
如果
不
存在
“调试”
。
“foo”
(
itemId
文本
,
last_update
时间戳
,
主
关键
(
itemId
)
)
;
声明
“test-cursor-crash”
光标
与
持有
为
选择
迪
。
itemId
从
“调试”
。
downloaded_images
迪
左
加入
(
选择
itemId
,
最小值
(
last_update
)
作为
last_update
从
“调试”
。
“foo”
集团
通过
itemId
)
计算
在
迪
。
itemId
=
计算
。
itemId
在哪里
合并
(
last_update
,
“1970-01-01”
)
&
lt
;
download_time
;
获取
10000年
在
“test-cursor-crash”
;
提交
;
|
从上面的例子在这里。通过做一些进一步的分析,它曝光了问题离开加入。对于等值连接,它能够正常工作。这个错误是固定在以后版本的PostgreSQL。
原因
如上所述,这个错误的真正原因是试图访问一个内存地址无法访问的计划,同样有各种各样的原因。然而,复杂的用户有一个有限的对这些概念的理解,因为,我将试图解释他们最简单的术语来解释。
以下是段错误的可能原因:
- 操作系统问题
- 车操作系统内核
- 硬件故障(特别是内存)
- 错误的产品(例如,PostgreSQL, MySQL)
- 数据库损坏
尽管这个错误的范围并不局限于上述原因,这些都是最可能的。为了了解问题的根源,需要用程序员的帮助解决它。
故障排除
深入研究段错误的根源,必须安装调试符号,使建立一个核心转储失败。这有助于分析问题,显示了功能或代码导致的问题的一部分。如果需求没有得到满足,它不能生成核心转储,它无法跟踪这个问题。
使核心转储生成
每个数据库都有不同的方法来生成核心转储文件。为了使一代的核心转储,需要设置一些内核设置如下。
在这里,可以使用任何其他路径而不是/var/crash.
|
1
2
|
#回声的内核。核心_pattern=/var/crash/core-%e-%p' >> /etc/sysctl.conf
# ulimit - c无限
|
启用调试
调试符号使代码级调试。它显示细节的文件被执行和行代码执行。负责软件开发人员可以构建调试符号。在PostgreSQL,调试符号可以启用的时候安装如下。
|
1
|
# . / configure CFLAGS = " o0 g3
|
有些包可在PostgreSQL,比如postgresql-12-dbg。
在MySQL中,以下命令在源代码安装可能打开调试。
|
1
|
# cmake -DWITH_DEBUG = 1
|
允许数据库生成核心转储
使核心转储生成和调试后,重要的是,数据库也应与主机操作系统生成一个核心转储。因此,数据库应该开始一个选项来创建核心文件。为了实现这个目标,一个人应该启动数据库的一个选择。
在PostgreSQL, pg_ctl命令应该开始使用- c选项,如下所示。
|
1
|
美元
/
usr
/
当地的
/
pgsql
/
本
- - - - - -
D
&
lt
;
data_directory
&
gt
;
- - - - - -
c
开始
|
含MySQL,以下行或my.ini。可以添加在my . cnf中所做
|
1
2
|
(
mysqld
]
核心
- - - - - -
文件
|
注意:在一个崩溃时,操作系统转储内存核心文件的所有内容。启用之前,确保你有足够的空间来容纳核心转储。
调试核心文件
核心文件是特定于版本的,他们可以读取特定的二进制版本的数据库。另一个版本的二进制文件无法读取的当前版本生成的核心文件数据库。像MySQL 8所产生的核心文件无法读取的MySQL二进制从任何其他版本。
可以跟踪核心转储Gnu调试器(gdb)。下面是一个例子,阅读核心转储。
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
|
美元
广东发展银行
/
usr
/
当地的
/
pgsql
/
本
/
postgres
/
var
/
崩溃
/
核心
- - - - - -
postgres
- - - - - -
64807年
GNU
广东发展银行
(
Ubuntu
9.2
- - - - - -
0 ubuntu1
~
20.04.1
)
9.2
版权
(
C
)
2020年
免费的
软件
基金会
,
公司
。
。
。
。
阅读
符号
从
/
usr
/
当地的
/
pgsql
/
本
/
postgres
。
。
。
(
新
LWP
64807年
]
(
线程
调试
使用
libthread_db
启用
]
使用
主机
libthread_db
图书馆
“/ lib / x86_64-linux-gnu / libthread_db.so.1”
。
核心
是
生成的
通过
”
postgres
:
postgres
postgres
(
当地的
]
提交”。
程序
终止
与
信号
SIGSEGV信号
,
分割
的错
。
# 0 slot_deform_heap_tuple(奈特= 2,offp = 0 x5560dcfd1d58,元组= & lt;优化out>,槽= 0 x5560dcfd1d10) execTuples.c: 930
930年
execTuples
。
c
:
没有
这样的
文件
或
目录
。
(
广东发展银行
)
|
除此之外,Valgrind也是一个工具,可以用来调试问题。了解更多关于Valgrind,看看分析内存使用MySQL与Valgrind地块。
雷竞技下载官网Percona的倡议
描述,一段错误引起的各种问题,有时甚至在程序员的控制。但是在许多情况下,程序本身是罪魁祸首,触发分割的缺点;然而,用户最不一样的知识。雷竞技下载官网Percona致力于加强开源社区,并承认这个问题。Perc雷竞技下载官网ona团队强烈认为,用户应该有知识的危险与一些非标准模块(或PostgreSQL扩展)被认为是麻烦制造者。
这些细节是计划中添加pg_gather报告。目前,这是在开发阶段。下一个版本可用的pg_gather将这些细节。
总结
事实上,段错误是一个问题,还没有广泛地探讨。已经说过,它经常由于各种原因再次使用数据库系统。基本上,它表面由于试图访问未经授权的地区或部分的内存,一个正常的DBA至少意识到是一样的。这个问题可以通过启用troubleshot核心转储生成和安装调试符号。




