IO_FILE-fread函数详解
August 2, 2019 PWN 访问: 40 次
#include<stdio.h>
int main()
{
char *a;
FILE *file_point = fopen("test.txt","r");
fread(a,1,12,file_point);
char *heap_point = malloc(0x20);
printf("%s",a);
return 0;
}
同样是带glibc源码进行调试
main函数下断点:
In file: /root/test/123.c
1 #include<stdio.h>
2 int main()
3 {
4 char *a;
5 FILE *file_point = fopen("test.txt","r");
► 6 fread(a,1,12,file_point);
7 char *heap_point = malloc(0x20);
8 printf("%s",a);
9 return 0;
10 }
s单步步入
In file: /root/glibc-2.23/libio/iofread.c
26
27 #include "libioP.h"
28
29 _IO_size_t
30 _IO_fread (void *buf, _IO_size_t size, _IO_size_t count, _IO_FILE *fp)
► 31 {
32 _IO_size_t bytes_requested = size * count;
33 _IO_size_t bytes_read;
34 CHECK_FILE (fp, 0);
35 if (bytes_requested == 0)
36 return 0;
iofread.c
源码如下
#include "libioP.h"
_IO_size_t
_IO_fread (void *buf, _IO_size_t size, _IO_size_t count, _IO_FILE *fp)
{
_IO_size_t bytes_requested = size * count;
_IO_size_t bytes_read;
CHECK_FILE (fp, 0);
if (bytes_requested == 0)
return 0;
_IO_acquire_lock (fp);
bytes_read = _IO_sgetn (fp, (char *) buf, bytes_requested);
_IO_release_lock (fp);
return bytes_requested == bytes_read ? count : bytes_read / size;
}
libc_hidden_def (_IO_fread)
#ifdef weak_alias
weak_alias (_IO_fread, fread)
# ifndef _IO_MTSAFE_IO
strong_alias (_IO_fread, __fread_unlocked)
libc_hidden_def (__fread_unlocked)
weak_alias (_IO_fread, fread_unlocked)
# endif
#endif
首先计算要读取的字节数_IO_size_t bytes_requested = size * count;
,然后判断是否为0,如果是0的话,就return 0
,然后调用_IO_sgetn
函数,单步步入发现_IO_sgetn
内部其实是调用了_IO_XSGETN
函数
_IO_size_t
_IO_sgetn (_IO_FILE *fp, void *data, _IO_size_t n)
{
/* FIXME handle putback buffer here! */
return _IO_XSGETN (fp, data, n);
}
查看_IO_XSGETN
函数的定义,其实是调用了vtable表中的__xsgetn
字段
#define _IO_XSGETN(FP, DATA, N) JUMP2 (__xsgetn, FP, DATA, N)