[20250117]记录下21c下使用gdb跟踪逻辑读遇到的问题.txt

news/2025/1/17 21:32:43/文章来源:https://www.cnblogs.com/lfree/p/18677706
[20250117]记录下21c下使用gdb跟踪逻辑读遇到的问题.txt

--//在21c下使用gdb跟踪逻辑读遇到的问题,困扰好几天,做一个记录。
--//首先我以前写过1个gdb脚本跟踪逻辑读在11g下,使用遇到一些问题,发现21c下没有使用kteinpscan,kdifxs函数。
--//我先注解这部分内容,测试看看。

1.环境:
SCOTT@book01p> @ ver2
==============================
PORT_STRING                   : x86_64/Linux 2.4.xx
VERSION                       : 21.0.0.0.0
BANNER                        : Oracle Database 21c Enterprise Edition Release 21.0.0.0.0 - Production
BANNER_FULL                   : Oracle Database 21c Enterprise Edition Release 21.0.0.0.0 - Production
Version 21.3.0.0.0
BANNER_LEGACY                 : Oracle Database 21c Enterprise Edition Release 21.0.0.0.0 - Production
CON_ID                        : 0
PL/SQL procedure successfully completed.

2.问题:
--//session 1:
SCOTT@book01p> @ spid
==============================
SID                           : 288
SERIAL#                       : 10960
PROCESS                       : 3443
SERVER                        : DEDICATED
SPID                          : 3445
PID                           : 42
P_SERIAL#                     : 4
KILL_COMMAND                  : alter system kill session '288,10960' immediate;
PL/SQL procedure successfully completed.

--//window 1:
$ rlgdb -f -p 3445 -x fetch21.gdb
...
/usr/src/debug/glibc-2.17-c758a686/sysdeps/unix/syscall-template.S:81:3374:beg:0x7ff024211480
Breakpoint 1 at 0x6f55db0
Breakpoint 2 at 0x14dd2840
Breakpoint 3 at 0x150bacb0
Breakpoint 4 at 0x14dd4740
Breakpoint 5 at 0x150a2220

--//session 1:
SCOTT@book01p> select * from emp ;

--//window 1:
(gdb) c
Continuing.
2025/01/17 09:23:14.578916428 :kteinpscan_int1 0x404728
2025/01/17 09:23:14.583312308 :kteinmap 0x404728
2025/01/17 09:23:14.588318301 :kdst_fetch 0x404729
2025/01/17 09:23:14.592462416 :kdst_fetch 0x40472a
2025/01/17 09:23:14.596911200 :kdst_fetch 0x40472b
2025/01/17 09:23:14.601128379 :kdst_fetch 0x40472c
2025/01/17 09:23:14.605677445 :kdst_fetch 0x40472d
2025/01/17 09:23:14.610015416 :kdst_fetch 0x40472e
2025/01/17 09:23:14.614121148 :kdst_fetch 0x40472f
2025/01/17 09:23:14.640008858 :kdsgrp 0x407d2c
2025/01/17 09:23:14.644933305 :kdsgrp 0x40717c
2025/01/17 09:23:14.650308734 :kdsgrp 0x406cff
2025/01/17 09:23:14.656093289 :kdsgrp 0x408b19
2025/01/17 09:23:14.673224752 :kteinpscan_int1 0x400ea8
2025/01/17 09:23:14.677325767 :kteinmap 0x400ea8
2025/01/17 09:23:14.682954100 :kdst_fetch 0x400ea9
2025/01/17 09:23:14.687107439 :kdst_fetch 0x400eaa
2025/01/17 09:23:14.691293112 :kdst_fetch 0x400eab
2025/01/17 09:23:14.695392614 :kdst_fetch 0x400eac
2025/01/17 09:23:14.699351668 :kdst_fetch 0x400ead
2025/01/17 09:23:14.703374736 :kdst_fetch 0x400eae
2025/01/17 09:23:14.707523855 :kdst_fetch 0x400eaf
2025/01/17 09:23:14.711629353 :kteinpscan_int1 0x404728
2025/01/17 09:23:14.715429348 :kteinmap 0x404728
2025/01/17 09:23:14.720132701 :kdst_fetch 0x404729
2025/01/17 09:23:14.723999463 :kdst_fetch 0x40472a
2025/01/17 09:23:14.728088980 :kdst_fetch 0x40472b
2025/01/17 09:23:14.732002462 :kdst_fetch 0x40472c
2025/01/17 09:23:14.735930066 :kdst_fetch 0x40472d
2025/01/17 09:23:14.739869374 :kdst_fetch 0x40472e
2025/01/17 09:23:14.743964729 :kdst_fetch 0x40472f
2025/01/17 09:23:14.748303359 :kdsgrp 0x400662
2025/01/17 09:23:14.752879915 :kdsgrp 0x4005cb
2025/01/17 09:23:14.758176698 :kdsgrp 0x404b0c
2025/01/17 09:23:14.777982961 :kdsgrp 0x100a253
2025/01/17 09:23:14.801122919 :kteinpscan_int1 0x3000092
2025/01/17 09:23:14.816837781 :kteinmap 0x3000092
--//注:在21c下没有kteinpscan函数,发现有kteinpscan_int1,使用它代替。
(gdb) b kteinpscan
Function "kteinpscan" not defined.
Make breakpoint pending on future shared library load? (y or [n]) n

(gdb) b kdifxs
Function "kdifxs" not defined.
Make breakpoint pending on future shared library load? (y or [n]) n

--//上面的看不见kdst_fetch函数调用,感觉有点奇怪。第1次执行看见许多递归调用很正常,仔细查看前面存在kdst_fetch的调用。
--//开始我的感觉前面的调用的对象dba地址是system文件下的dba地址,而其他users表空间的数据文件地址不记录,为什么?
--//我尝试设置alter system set "_trace_pin_time"=true scope=spfile;,重启数据库没用。而且我发现pin信息并不会记录在跟踪文
--//件里面,在cdb以及pdb下问题一样,也就是设置"_trace_pin_time"=true在21c下没用。另外gdb跟踪脚本仅仅对于数据文件1才会出
--//现kdst_fetch,不理解为什么出现这样的情况。

--//再走了许多弯路以后,最终发现打开10046跟踪就可以看到kdst_fetch的函数调用,不理解为什么出现这样的情况?
--//session 1:
SCOTT@book01p> @ 10046on 12
Session altered.

SCOTT@book01p> select * from emp ;

--//window 1:
2025/01/17 09:32:20.999570936 :kteinpscan_int1 0x3000092
2025/01/17 09:32:21.004062660 :kteinmap 0x3000092
2025/01/17 09:32:21.008996090 :kdst_fetch 0x3000093
2025/01/17 09:32:21.013613286 :kdst_fetch 0x3000094
2025/01/17 09:32:21.017875027 :kdst_fetch 0x3000095
2025/01/17 09:32:21.025932281 :kdst_fetch 0x3000096
2025/01/17 09:32:21.030022441 :kdst_fetch 0x3000096
2025/01/17 09:32:21.034238364 :kdst_fetch 0x3000097

3.继续其他测试:
--//session 1:
--//INDEX FAST FULL SCAN
SCOTT@book01p> select /*+ index_ffs(emp) */ count(*) from emp;

  COUNT(*)
----------
        14


--//window 1:
2025/01/17 09:35:57.915491960 :kteinpscan_int1 0x300009a
2025/01/17 09:35:57.920081950 :kteinmap 0x300009a
2025/01/17 09:35:57.924230311 :kteinpscan_int1 0x300009a
2025/01/17 09:35:57.928508887 :kteinmap 0x300009a
--//避免递归,你可以执行多次,少量1个数据块。

--//session 1:
--// TABLE ACCESS BY USER ROWID
SCOTT@book01p> select * from emp where rowid='AAASmhAAMAAAACWAAU';

     EMPNO ENAME      JOB              MGR HIREDATE                   SAL       COMM     DEPTNO
---------- ---------- --------- ---------- ------------------- ---------- ---------- ----------
      7788 SCOTT      ANALYST         7566 1987-07-13 00:00:00       3000                    20

--//window 1:
2025/01/17 09:37:58.553438472 :kdsgrp 0x3000096

--//session 1:
--//INDEX RANGE SCAN   
SCOTT@book> select * from emp where empno  between 7788 and 7900;

--//window 1:
2025/01/17 09:40:03.876476030 :kdsgrp 0x3000096
--//缺少了kdifxs函数,导致我写的gdb脚本记录kdsgrp仅仅出现1次。

$ strings $(which oracle) | grep  -i kdifxs| head -3
kdifxs1
kmdrdbmsKdifxs
kdifxs0
--//乱猜测一下,现在使用的是kdifxs0。

--//session 1:
--//INDEX RANGE SCAN   
SCOTT@book> select * from emp where empno  between 7788 and 7900;

--//window 1:
2025/01/17 15:52:14.174940268 :kdifxs0 0x300009b
2025/01/17 15:52:14.180038004 :kdsgrp 0x3000096
2025/01/17 15:52:14.188875295 :kdifxs0 0x300009b
2025/01/17 15:52:14.193290174 :kdsgrp 0x3000096

--//修改gdb脚本如下,记住要使用打开10046跟踪,虽然自己不理解为什么,为什么不打开10046的情况下跟踪不到kdst_fetch函数
--//调用。

$ grep -v "^#" fetch21.gdb
set $a=0x0
set $b=0x0

break __read_nocancel
set pagination off
commands
    silent
    set $a=0x0
    set $b=0x0
    continue
end


break kteinpscan_int1
set pagination off
  commands
    silent
    shell echo -n $( date +"%Y/%m/%d %T.%N : ")
    printf "kteinpscan_int1 0x%x\n", *($rdi+4)
    continue
  end

break kdst_fetch if *($rsi+28) != 0x0
set pagination off
  commands
    silent
    shell echo -n $( date +"%Y/%m/%d %T.%N : ")
    printf "kdst_fetch 0x%x\n", *($rsi+28)
    continue
  end

break kteinmap
set pagination off
  commands
    silent
    shell echo -n $( date +"%Y/%m/%d %T.%N : ")
    printf "kteinmap 0x%x\n", *($rdi+4)
    continue
  end

break kdifxs0 if *($rdi+28) != $a
set pagination off
  commands
    silent
    shell echo -n $( date +"%Y/%m/%d %T.%N : ")
    printf "kdifxs0 0x%x\n",*($rdi+28)
        set $a= *($rdi+28)
   continue
  end


break kdsgrp if *($rdi+28) != $b
set pagination off
  commands
    silent
    shell echo -n $( date +"%Y/%m/%d %T.%N : ")
    printf "kdsgrp 0x%x\n", *($rdi+28)
        set $b= *($rdi+28)
    continue
  end

--//简单说明一下:11g下初始化变量a,b时,设置断点在snttread,21c下修改__read_nocance。
--//执行gdb 跟踪会话,执行如下很容易确定:

(gdb) bt 3
#0  0x00007fd032ab7480 in __read_nocancel () at ../sysdeps/unix/syscall-template.S:81
#1  0x0000000015415605 in read ()
#2  0x000000001540f360 in snttread ()
(More stack frames follow...)

4.如果执行INDEX FULL SCAN呢?
--//session 1:
--//INDEX FULL SCAN
SCOTT@book01p> select /*+ index_ffs(emp) */ count(*) from emp;

--//window 1:
2025/01/17 15:56:51.284515751 :kdifxs0 0x300009b
--//仅仅看到1次。

SCOTT@book01p> @ dpc '' '' ''
PLAN_TABLE_OUTPUT
-------------------------------------
SQL_ID  72rq2sakdcx3h, child number 1
-------------------------------------
select  count (*)  from emp
Plan hash value: 2937609675
-------------------------------------------------------------------------------------------------------------
| Id  | Operation        | Name   | Starts | E-Rows | Cost (%CPU)| E-Time   | A-Rows |   A-Time   | Buffers |
-------------------------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT |        |      1 |        |     1 (100)|          |      1 |00:00:00.01 |       1 |
|   1 |  SORT AGGREGATE  |        |      1 |      1 |            |          |      1 |00:00:00.01 |       1 |
|   2 |   INDEX FULL SCAN| PK_EMP |      1 |     12 |     1   (0)| 00:00:01 |     14 |00:00:00.01 |       1 |
-------------------------------------------------------------------------------------------------------------
Query Block Name / Object Alias (identified by operation id):
-------------------------------------------------------------
   1 - SEL$1
   2 - SEL$1 / "EMP"@"SEL$1"
--//逻辑读1次

SCOTT@book01p> select /*+ index_ffs(emp)  */ count (*)  from emp ;
  COUNT(*)
----------
        14
SCOTT@book01p> @ dpc '' '' ''
PLAN_TABLE_OUTPUT
-------------------------------------
SQL_ID  1fytxx868arn9, child number 0
-------------------------------------
select /*+ index_ffs(emp)  */ count (*)  from emp
Plan hash value: 1006289799
------------------------------------------------------------------------------------------------------------------
| Id  | Operation             | Name   | Starts | E-Rows | Cost (%CPU)| E-Time   | A-Rows |   A-Time   | Buffers |
------------------------------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT      |        |      1 |        |     2 (100)|          |      1 |00:00:00.02 |       4 |
|   1 |  SORT AGGREGATE       |        |      1 |      1 |            |          |      1 |00:00:00.02 |       4 |
|   2 |   INDEX FAST FULL SCAN| PK_EMP |      1 |     12 |     2   (0)| 00:00:01 |     14 |00:00:00.02 |       4 |
------------------------------------------------------------------------------------------------------------------
Query Block Name / Object Alias (identified by operation id):
-------------------------------------------------------------
   1 - SEL$1
   2 - SEL$1 / "EMP"@"SEL$1"
Hint Report (identified by operation id / Query Block Name / Object Alias):
Total hints for statement: 1
---------------------------------------------------------------------------
   2 -  SEL$1 / "EMP"@"SEL$1"
           -  index_ffs(emp)
--//逻辑读4次.注:在11g下测试3个逻辑读。
--//window 1:
2025/01/17 15:58:40.540827345 :kteinpscan_int1 0x300009a
2025/01/17 15:58:40.545174023 :kteinmap 0x300009a
2025/01/17 15:58:40.549210158 :kteinpscan_int1 0x300009a
2025/01/17 15:58:40.553239713 :kteinmap 0x300009a
--//少记录0x300009b,不知道调用什么函数。调用kdirfrs。

--//顺便贴上当时在11g的测试:
--//INDEX FAST FULL SCAN
select /*+ index_ffs(emp) */ count(*) from emp;
--//跟踪文件:
*** 2021-02-20 15:36:45.413
pin ktewh26: kteinpscan dba 0x100009a:4 time 2708712237
pin kdiwh100: kdircys dba 0x100009b:1 time 2708717602
~~~~~~~~~~~~~//没有kdircys函数。
--//gdb显示:
2021/02/20 15:36:45.400717820 :kteinpscan 0x100009a
2021/02/20 15:36:45.406515456 :kteinmap 0x100009a
2021/02/20 15:36:45.411622200 :kteinpscan 0x100009a
2021/02/20 15:36:45.416993772 :kteinmap 0x100009a

5.如果执行INDEX UNIQUE SCAN呢?
--//session 1:
SCOTT@book01p> select * from emp where empno  = 7788 ;
     EMPNO ENAME      JOB              MGR HIREDATE                   SAL       COMM     DEPTNO
---------- ---------- --------- ---------- ------------------- ---------- ---------- ----------
      7788 SCOTT      ANALYST         7566 1987-07-13 00:00:00       3000                    20

--//window 1:
2025/01/17 16:30:48.505308120 :kdsgrp 0x3000096
--//看不到索引块。做了一下跟踪,好像调用kdifkc函数。

--//最终修改如下,记录开始10046跟踪才能看到kdst_fetch 的调用。
$ grep -v "^#" fetch21.gdb | cat -s
set pagination off
set $a=0x0
set $b=0x0
set $c=0x0
set $d=0x0

break __read_nocancel
commands
    silent
    set $a=0x0
    set $b=0x0
    set $c=0x0
    set $d=0x0
    continue
end

break kteinpscan_int1
  commands
    silent
    shell echo -n $( date +"%Y/%m/%d %T.%N : ")
    printf "kteinpscan_int1 0x%x\n", *($rdi+4)
    continue
  end

break kdst_fetch if *($rsi+28) != 0x0
  commands
    silent
    shell echo -n $( date +"%Y/%m/%d %T.%N : ")
    printf "kdst_fetch 0x%x\n", *($rsi+28)
    continue
  end

break kteinmap
  commands
    silent
    shell echo -n $( date +"%Y/%m/%d %T.%N : ")
    printf "kteinmap 0x%x\n", *($rdi+4)
    continue
  end

break kdifxs0 if *($rdi+28) != $a
  commands
    silent
    shell echo -n $( date +"%Y/%m/%d %T.%N : ")
    printf "kdifxs0 0x%x\n",*($rdi+28)
        set $a= *($rdi+28)
   continue
  end

break kdirfrs if *($rdi+28) != $c
  commands
    silent
    shell echo -n $( date +"%Y/%m/%d %T.%N : ")
    printf "kdirfrs 0x%x\n",*($rdi+28)
        set $c= *($rdi+28)
   continue
  end

break kdifkc if *($rsi+36) != $d
  commands
    silent
    shell echo -n $( date +"%Y/%m/%d %T.%N : ")
    printf "kdifkc 0x%x\n",*($rsi+36)
        set $d= *($rsi+36)
   continue
  end

break kdsgrp if *($rdi+28) != $b
  commands
    silent
    shell echo -n $( date +"%Y/%m/%d %T.%N : ")
    printf "kdsgrp 0x%x\n", *($rdi+28)
        set $b= *($rdi+28)
    continue
  end

--//不能作为逻辑读数量依据,仅仅作为参考。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/870970.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

WSL2配置代理

1、关闭梯子 2、设置为mirrored模式该设置会生成 C:/Users//.wslconfig【可选】修改.wslconfig文件内容如下 [experimental] autoMemoryReclaim=gradual networkingMode=mirrored dnsTunneling=true firewall=true autoProxy=true3、打开cmd并执行wsl --shutdown 4、重新启动…

【MySQL架构】图解

你是一个程序员,你做了一个网站应用,站点里的用户数据,需要存到某个地方,方便随时读写。 很容易想到可以将数据存到文件里。 但如果数据量很大,想从大量文件数据中查找某部分数据,并更新,是一件很痛苦的事情。 那么问题就来了,有办法可以解决这个问题吗? 好办,没有什…

2025 郑州一测 T18: 双变量问题探讨

2025 高考加把劲 /qtContent已知函数 \(f(x) = \log_a x(a>0, a\neq 1)\), \(y = f(x)\) 关于 \(y=x\) 对称的函数记为 \(g(x)\). (I) 若 \(a>1\), 方程 \(f(x)-g(x)=0\) 有且仅有一个实数解, 求 \(a\) 的值. (II) 讨论方程 \(g(x) = x_a = 0\) 在 \((0, +\infty)\) 上实…

笑死

哈哈哈哈哈笑死这个中国银行的标志出现的恰到好处,我还以为是什么标识

C#数据结构与算法入门实战指南

前言 在编程领域,数据结构与算法是构建高效、可靠和可扩展软件系统的基石。它们对于提升程序性能、优化资源利用以及解决复杂问题具有至关重要的作用。今天大姚分享一些非常不错的C#数据结构与算法实战教程,希望可以帮助到有需要的小伙伴。 C#经典十大排序算法 主要讲解C#经典…

29. 数据库操作

一、SQL与数据库数据库 (database)是统一管理的、有组织的、可共享的大量数据的集合。数据库将数据存储在一个或多个表格中,管理这个数据库的软件称为 数据库管理系统(database management system, DBMS)。数据库不是针对具体的应用程序,而是立足于数据本身的管理,它将所…

用Mermaid画图

1、用Mermaid画图 mermaid.md TyporaPortable.rar mermaid.zip 目录1 Mermaid是什么1.1 概述1.2 网址官网地址:Github地址:图形图形几种图形名字节点与无名字节点设置样式:style, classDef, class, :::线条图形连线(--)及注释(%%)线条样式实线与虚线箭头实线与粗实线及箭头延…

【RabbitMQ】图解

你是一个程序员,假设你维护了两个服务 A 和 B。 A 服务负责转发用户请求到 B 服务,B 服务是个算法服务,GPU 资源有限,当请求量大到 B 服务处理不过来的时候,希望能优先处理会员用户的请求。 那么问题就来了,如果普通用户和会员用户同时发起请求,怎样才能做到会员优先呢?…

THREE.js学习笔记8——Textures

这个小节主要学习纹理,Texture 纹理是覆盖几何形状表面的图像,不同类型的纹理具有多种不同的效果。 这些纹理(尤其是金属性和粗糙度)遵循PBR原则基于物理的渲染 许多技术往往遵循现实生活中的方向以获得现实的结果 成为现实渲染的标准 许多软件、引擎和库都在使用它如何加载…

快速傅里叶变换总结

基本概念 对于求和式 \(\sum a_ix^i\),如果是有限项相加,称为多项式,记作 \[f(x)=\sum_{i=0}^n a_ix^i。 \]其中最高次项的次数为 \(n\),为 \(n\) 次多项式。 用 \(n+1\) 个点可以唯一地确定一个 \(n\) 次多项式,这一过程可以参考 拉格朗日插值。 引入 给定多项式 \(f(x),…

寒假学习1

老年人评估系统 初步整理web端思路先写了第一张信息表并搭建基本框架并编写了老年人信息添加功能

1.17安卓测试

今天在idea进行安卓虚拟机测试成功,昨天的错误是因为版本不兼容 启动虚拟机运行测试