在我的计算机上运行以下代码(make runtest
)
4.6.4-1-ARCH
的产率:
/* scanf userland & kernelspace test */
#if __KERNEL__
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/string.h>
MODULE_AUTHOR("Enteee (duckpond.ch) ");
MODULE_DESCRIPTION("scanf test");
MODULE_LICENSE("GPL");
MODULE_ALIAS("scanf_test");
#else
#include <stdio.h>
#include <string.h>
#define printk printf
#endif
void test(void){
int ret = 0;
char fp[20] = { 0 };
memset(fp, 0xaa, sizeof(fp));
printk("init, ret = %d fp = "
"%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx"
"%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx"
"%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx"
"%2.2hhx%2.2hhx, "
// overflow prints (hacky)
"after fp = "
"%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx, "
"before fp = "
"%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx"
"\n",
ret,
(fp)[0], (fp)[1], (fp)[2], (fp)[3], (fp)[4], (fp)[5],
(fp)[6], (fp)[7], (fp)[8], (fp)[9], (fp)[10], (fp)[11],
(fp)[12], (fp)[13], (fp)[14], (fp)[15], (fp)[16], (fp)[17],
(fp)[18], (fp)[19],
// overflow
(fp)[20], (fp)[21], (fp)[22], (fp)[23], (fp)[24], (fp)[25],
(fp)[-1], (fp)[-2], (fp)[-3], (fp)[-4], (fp)[-5], (fp)[-6]
);
ret = sscanf("aabb", "%2hhx%2hhx", &fp[0], &fp[1]);
printk("ret = %d fp = %2.2hhx%2.2hhx\n", ret, fp[0], fp[1]);
ret = sscanf(
"ffffffffffffffffffffffffffffffffffffffff",
"%2hhx%2hhx%2hhx%2hhx%2hhx%2hhx"
"%2hhx%2hhx%2hhx%2hhx%2hhx%2hhx"
"%2hhx%2hhx%2hhx%2hhx%2hhx%2hhx"
"%2hhx%2hhx",
&(fp)[0], &(fp)[1], &(fp)[2], &(fp)[3], &(fp)[4], &(fp)[5],
&(fp)[6], &(fp)[7], &(fp)[8], &(fp)[9], &(fp)[10], &(fp)[11],
&(fp)[12], &(fp)[13], &(fp)[14], &(fp)[15], &(fp)[16], &(fp)[17],
&(fp)[18], &(fp)[19]
);
printk("ret = %d fp = "
"%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx"
"%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx"
"%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx"
"%2.2hhx%2.2hhx, "
// overflow prints (hacky)
"after fp = "
"%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx, "
"before fp = "
"%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx%2.2hhx"
"\n",
ret,
(fp)[0], (fp)[1], (fp)[2], (fp)[3], (fp)[4], (fp)[5],
(fp)[6], (fp)[7], (fp)[8], (fp)[9], (fp)[10], (fp)[11],
(fp)[12], (fp)[13], (fp)[14], (fp)[15], (fp)[16], (fp)[17],
(fp)[18], (fp)[19],
(fp)[20], (fp)[21], (fp)[22], (fp)[23], (fp)[24], (fp)[25],
(fp)[-1], (fp)[-2], (fp)[-3], (fp)[-4], (fp)[-5], (fp)[-6]
);
}
#ifndef __KERNEL__
int main(void){
test();
return 0;
}
#else
static int __init test_init(void) {
test();
return 0;
}
static void __exit test_exit(void) {
}
module_init(test_init);
module_exit(test_exit);
#endif
test.c基本上使用=== user space ===
init, ret = 0 fp = aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa, after fp = 65005f5f7664, before fp = 000000000000
ret = 2 fp = aabb
ret = 20 fp = ffffffffffffffffffffffffffffffffffffffff, after fp = 65005f5f7664, before fp = 000000000000
=== kernel space ===
[386177.161037] init, ret = 0 fp = aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa, after fp = baae0dbc0000, before fp = bc0daebaffff
[386177.161044] ret = 2 fp = aabb
[386177.161061] ret = 20 fp = 000000000000000000000000ffffffffffffffff, after fp = baae0dbc0000, before fp = bc0daebaffff
使用ffffffffffffffffffffffffffffffffffffffff
格式说明符序列将fp
读取为sscanf
。之后,它会使用%2hhx
/ fp
打印printf
,并使用printk
格式说明符序列。
当有人使用glibc sscanf和linux sscanf阅读时,有人可以解释为什么%2.2hhx
不一样。另外,为什么fp
- 测试工作得很好?
我已经检查了linux sscanf的影响,从我看到它应该与glibc sscanf类似。
我确实认为我在这里错过了显而易见的事实。
注意: