[20261007]关于oracle sskgph2函数.txt
--//在计算Semaphore Arrays Key时发现调用sskgpwidtokeys,跟踪整个过程时发现如下信息:
# bpftrace sskgphpjw.bt 0
Attached 9 probes
sskgpwidtokeys Begin
sskgpbitspersem Begin
[14:57:00] sskgpbitspersem pid=3295 return hash_value=0x0000000e 14
sskgpbitspersem End
[14:57:00] sskgphpjw pid=3295 ptr=0x00007ffec4d01460 len=43 str=book/u01/app/oracle/product/21.0.0/dbhome_1
[14:57:00] sskgphpjw pid=3295 return hash_value=0x5507207c 1426530428
[14:57:00] sskgphpjw pid=3295 ptr=0x00007ffec4d01460 len=43 str=cppl0v120bqq0psbdmf0qspevdu032/1/10ecipnf`2
[14:57:00] sskgphpjw pid=3295 return hash_value=0x7e0edb60 2114902880
[14:57:00] sskgphpjw pid=3295 ptr=0x00007ffec4d01460 len=43 str=dqqm1w231crr1qtceng1rtqfwev14302021fdjqoga3
[14:57:00] sskgphpjw pid=3295 return hash_value=0x99eaaedc 2582294236
[14:57:00] sskgphpjw pid=3295 ptr=0x00007ffec4d01460 len=43 str=errn2x342dss2rudfoh2surgxfw25413132gekrphb4
[14:57:00] sskgphpjw pid=3295 return hash_value=0x32fcf5bc 855438780
sskgph2 Begin
[14:57:00] sskgph2 pid=3295 ptr=0x00007ffec4d01cb8 len=43 str=book/u01/app/oracle/product/21.0.0/dbhome_1
[14:57:00] sskgph2 pid=3295 return hash_value=0x9937c3fd 2570568701
sskgph2 End
sskgpwidtokeys End
--//可以发现sskgph2参与运算的字符串是book/u01/app/oracle/product/21.0.0/dbhome_1,sid+ORACLE_HOME.
--//返回0x9937c3fd 2570568701。 为什么oracle计算类似hash值,搞出这么多算法,也许避免重复.
--//没事做一点点简单探究:
$ ./lookup.awk sskgph2
(sskgp)h2 : operating system dependent system kernel generic process ??
1.看看保存在内存那个位置:
--//我以前使用dumpsga做过整个sga的转储,可以使用它查看在内存的某个位置.
$ cd ~/sga/Aug_12_16:41:17_2026
$ od -Ax -v -w64 -t x4 61000000 | grep -C3 9937c3fd
1d6b6040 00000000 00000000 00000000 00000000 00000000 00000000 000003c3 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000209 00000000
1d6b6080 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000031 00b38f00
1d6b60c0 15a1aa78 00000000 fffffefe fffdffff 0000000f 00000000 00000000 00000000 00000000 00000000 00000401 00b38f00 15a1aa88 00000000 000000f6 00000009
1d6b6100 00000000 00000000 0000d431 0000d431 000000fa 000000f6 000000fa 00000001 00000004 9937c3fd 0000000e 00000000 00000000 00000000 00000000 00000000
~~~~~~~~
1d6b6140 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000
1d6b6180 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000
1d6b61c0 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000
--//位于 0x1d6b6100+0x61000000+0x9*4 = 0x7e6b6124,仅仅出现1处。其他共享内存段没有发现。
SYS@book> @ fchaz 0x7e6b6100
LOC KSMCHPTR KSMCHIDX KSMCHDUR KSMCHCOM KSMCHSIZ KSMCHCLS KSMCHTYP KSMCHPAR KSMCHPTR_BEGIN KSMCHPTR_END+1
---- ---------------- ---------- ---------- -------------------------------- ---------- -------- ---------- ---------------- ---------------- -----------------
VSGA 000000007E6B60E8 1 1 generic process 1024 perm 0 000000007E0CD000 000000007E6B60E8 000000007E6B64E8
--//占用1024字节.
SYS@book> @ opeek 000000007E6B60E8 1024 1
New tracefile_identifier = /u01/app/oracle/diag/rdbms/book/book/trace/book_ora_5051_0001.trc
[07E6B60E8, 07E6B64E8) = 00000401 00B38F00 15A1AA88 00000000 000000F6 00000009 00000000 00000000 0000D431 0000D431 000000FA 000000F6 000000FA 00000001 ...
--//查看跟踪文件:
*** 2026-10-07T15:05:02.806763+08:00 (CDB$ROOT(1))
Processing Oradebug command 'peek 0x000000007e6b60e8 1024 1'
[07E6B60E8, 07E6B64E8) = 00000401 00B38F00 15A1AA88 00000000 000000F6 ...
Dump of memory from 0x07E6B60FC to 0x07E6B64E8
07E6B60F0 00000009 [....]
07E6B6100 00000000 00000000 0000D431 0000D431 [........1...1...]
07E6B6110 000000FA 000000F6 000000FA 00000001 [................]
07E6B6120 00000004 9937C3FD 0000000E 00000000 [......7.........]
07E6B6130 00000000 00000000 00000000 00000000 [................]
Repeat 24 times
07E6B62C0 7E6B6CB8 00000000 00000000 00000000 [.lk~............]
07E6B62D0 00000000 00000000 00000000 00000000 [................]
Repeat 32 times
07E6B64E0 00000000 00000000 [........]
--//直接使用xxd查看内存:
$ pgrep mmon
3397
$ xxd -a -c 32 -g 4 -s 0x000000007E6B60E8 -l 1024 /proc/$(pgrep pmon)/mem
7e6b60e8: 01040000 008fb300 88aaa115 00000000 f6000000 09000000 00000000 00000000 ................................
7e6b6108: 31d40000 31d40000 fa000000 f6000000 fa000000 01000000 04000000 fdc33799 1...1.........................7.
7e6b6128: 0e000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 ................................
7e6b6148: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 ................................
*
7e6b62a8: 00000000 00000000 00000000 00000000 00000000 00000000 b86c6b7e 00000000 .........................lk~....
7e6b62c8: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 ................................
*
7e6b64c8: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 ................................
--//在下划线位置.intel cpu 的litter endian。大小头对调 9937c3fd。
--//4字节对调如下:
$ xxd -c 32 -g 4 -p -s 0x000000007E6B60E8 -l 1024 /proc/$(pgrep pmon)/mem | xxd -r -p | od -t x4 -w32
0000000 00000401 00b38f00 15a1aa88 00000000 000000f6 00000009 00000000 00000000
0000040 0000d431 0000d431 000000fa 000000f6 000000fa 00000001 00000004 9937c3fd
0000100 0000000e 00000000 00000000 00000000 00000000 00000000 00000000 00000000
0000140 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000
*
0000700 00000000 00000000 00000000 00000000 00000000 00000000 7e6b6cb8 00000000
0000740 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000
*
0002000
--//0xf6 = 246
--//0xfa = 250
--//估计与oracle processes参数有关,可以尝试修改processes参数为其他值,启动数据库实例,查询x$ksmsp的KSMCHCOM='generic
--// process'。
SYS@book> @ hidez ^processes$
SYS@book> @ pr
==============================
NUM : 52
N_HEX : 34
CON_ID : 0
NAME : processes
DESCRIPTION : user processes
DEFAULT_VALUE : FALSE
SESSION_VALUE : 246
SYSTEM_VALUE : 246
ISSES_MODIFIABLE : FALSE
ISSYS_MODIFIABLE : IMMEDIATE
PL/SQL procedure successfully completed.
--//0x0000d431 = 54321,估计oracle用户的uid以及gid。
$ id
uid=54321(oracle) gid=54321(oinstall) groups=54321(oinstall),54322(dba),54323(oper) context=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c1023
--// 0x7e6b6cb8 估计对应某个地址。
SYS@book> @ fchaz 7e6b6cb8
LOC KSMCHPTR KSMCHIDX KSMCHDUR KSMCHCOM KSMCHSIZ KSMCHCLS KSMCHTYP KSMCHPAR KSMCHPTR_BEGIN KSMCHPTR_END+1
---- ---------------- ---------- ---------- -------------------------------- ---------- -------- ---------- ---------------- ---------------- -----------------
VSGA 000000007E6B6CA8 1 1 sskgpwcr: Sem s 24 perm 0 000000007E0CD000 000000007E6B6CA8 000000007E6B6CC0
--//感觉好像是这个意思。
--//0x7e6b6cb8-0x000000007E6B6CA8 = 16,偏移chunk的第16字节。
SYS@book> @ opeek 000000007E6B6CA8 24 0
[07E6B6CA8, 07E6B6CC0) = 00000019 00B38F00 17A80ED0 00000000 00008005 00000000
--//00008005 = 32773.
$ ipcs -m -s
------ Shared Memory Segments --------
key shmid owner perms bytes nattch status
0x00000000 48 oracle 600 10485760 56
0x00000000 49 oracle 600 1140850688 56
0x00000000 50 oracle 600 8388608 56
0xafa94c20 51 oracle 600 2097152 56
------ Semaphore Arrays --------
key semid owner perms nsems
0x5507207c 32773 oracle 600 250
--//估计对应semid=32773。
--//以上都是猜测,可以增加Semaphore Arrays的数量加以确认。
2.继续测试:
--//关闭数据库实例,修改内核参数:
# sysctl -w "kernel.sem = 30 32000 250 12"
kernel.sem = 30 32000 250 12
--//重启数据库略:
$ ipcs -m -s
------ Shared Memory Segments --------
key shmid owner perms bytes nattch status
0x00000000 52 oracle 600 10485760 55
0x00000000 53 oracle 600 1140850688 55
0x00000000 54 oracle 600 8388608 55
0xafa94c20 55 oracle 600 2097152 55
------ Semaphore Arrays --------
key semid owner perms nsems
0x5507207c 32777 oracle 600 30
0x5507207d 32778 oracle 600 30
0x5507207e 32779 oracle 600 30
0x5507207f 32780 oracle 600 30
0x55072080 32781 oracle 600 30
0x55072081 32782 oracle 600 30
0x55072082 32783 oracle 600 30
0x55072083 32784 oracle 600 30
0x55072084 32785 oracle 600 30
0x55072085 32786 oracle 600 30
--//建立10个Semaphore Arrays。
SYS@book> select * from x$ksmsp where KSMCHCOM='generic process';
ADDR INDX INST_ID CON_ID KSMCHIDX KSMCHDUR KSMCHCOM KSMCHPTR KSMCHSIZ KSMCHCLS KSMCHTYP KSMCHPAR
---------------- ---------- ---------- ---------- ---------- ---------- -------------------------------- ---------------- ---------- -------- ---------- ----------------
00007F734DE94C18 20812 1 1 1 1 generic process 000000007E6B60E8 1024 perm 0 000000007E0CD000
$ xxd -c 32 -g 4 -p -s 0x000000007E6B60E8 -l 1024 /proc/$(pgrep pmon)/mem | xxd -r -p | od -t x4 -w32
0000000 00000401 00b38f00 15a1aa88 00000000 000000f6 00000009 00000000 00000000
0000040 0000d431 0000d431 0000001e 0000001a 0000001e 0000000a 00000004 9937c3fd
0000100 0000000e 00000000 00000000 00000000 00000000 00000000 00000000 00000000
0000140 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000
*
0000700 00000000 00000000 00000000 00000000 00000000 00000000 7e6b6cb8 00000000
0000740 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000
*
0002000
--//0x1e = 30,对应nsems。
--//0x1a = 26
$ ipcs -s -i 32777
Semaphore Array semid=32777
uid=54321 gid=54321 cuid=54321 cgid=54321
mode=0600, access_perms=0600
nsems = 30
otime = Wed Oct 7 15:33:10 2026
ctime = Wed Oct 7 15:27:04 2026
semnum value ncount zcount pid
0 1 0 0 5221
1 17405 0 0 5221
2 25823 0 0 5221
3 32761 0 0 5221
4 0 0 0 0
5 0 0 0 0
6 0 1 0 5239
7 0 1 0 5243
8 0 1 0 5247
9 0 0 0 0
10 0 1 0 5257
11 0 1 0 5261
12 0 1 0 5334
13 0 1 0 5267
14 0 1 0 5267
15 0 1 0 5269
16 0 1 0 5273
17 0 1 0 5275
18 0 1 0 5278
19 0 1 0 5278
20 0 1 0 5280
21 0 1 0 5282
22 0 1 0 5284
23 0 1 0 5286
24 0 1 0 5293
25 0 1 0 5295
26 0 1 0 5299
27 0 1 0 5301
28 0 1 0 5303
29 0 1 0 5305
--//前4个不使用,剩下26.
--//看看最后1个Semaphore Arrays:
$ ipcs -s -i 32786
Semaphore Array semid=32786
uid=54321 gid=54321 cuid=54321 cgid=54321
mode=0600, access_perms=0600
nsems = 30
otime = Wed Oct 7 15:27:05 2026
ctime = Wed Oct 7 15:27:04 2026
semnum value ncount zcount pid
0 0 0 0 5221
1 17405 0 0 5221
2 25823 0 0 5221
3 32761 0 0 5221
4 0 0 0 0
5 0 0 0 0
6 0 0 0 0
7 0 0 0 0
8 0 0 0 0
9 0 0 0 0
10 0 0 0 0
11 0 0 0 0
12 0 0 0 0
13 0 0 0 0
14 0 0 0 0
15 0 0 0 5221
16 0 0 0 0
17 0 0 0 0
18 0 0 0 0
19 0 0 0 0
20 0 0 0 0
21 0 0 0 0
22 0 0 0 0
23 0 0 0 0
24 0 0 0 0
25 0 0 0 0
26 0 0 0 0
27 0 0 0 0
28 0 0 0 0
29 0 0 0 0
--//最后1组,仅仅到semnum=15,仅仅11个可用。
--//0x0a估计表示有10个Semaphore Arrays。
--//写入semnum的value=17405,25823,32761,每次都是一样的,表示什么意思。
--//看看7e6b6cb8
SYS@book> @ fchaz 7e6b6cb8
LOC KSMCHPTR KSMCHIDX KSMCHDUR KSMCHCOM KSMCHSIZ KSMCHCLS KSMCHTYP KSMCHPAR KSMCHPTR_BEGIN KSMCHPTR_END+1
---- ---------------- ---------- ---------- -------------------------------- ---------- -------- ---------- ---------------- ---------------- -----------------
VSGA 000000007E6B6CA8 1 1 sskgpwcr: Sem s 56 perm 0 000000007E0CD000 000000007E6B6CA8 000000007E6B6CE0
SYS@book> @ opeek 000000007E6B6CA8 56 0
[07E6B6CA8, 07E6B6CE0) = 00000039 00B38F00 17A80ED0 00000000 00008009 0000800A 0000800B 0000800C 0000800D 0000800E 0000800F 00008010 00008011 00008012
--//0x00008009 = 32777
--//0x00008012 = 32786
--//确实是semid,完全对上。
--//纯粹乱猜.
--//提交deepseek看看我的分析是否存在什么问题,解答如下:
在跟踪 sskgpwidtokeys 时,sskgphpjw 对 SID+ORACLE_HOME 计算出最终 semaphore key 0x5507207c,与 ipcs 中的 Semaphore
Arrays key 一致。
sskgph2 对同一字符串又计算出一个内部 hash 0x9937c3fd,该值保存在 SGA 的 generic process chunk 中,地址 0x7E6B6124,并和
bits per sem=14、processes=246、semmsl、每数组可用信号量数、数组个数等字段相邻。
sskgpwcr: Sem s chunk 中保存的是实际 semid 列表,修改 kernel.sem 后从单个 32773 变成 32777..32786,与 ipcs 完全对应。
来自 “ ITPUB博客 ” ,链接:https://blog.itpub.net/267265/viewspace-3184558/ ,如需转载,请注明出处,否则将追究法律责任。