index.dat文件剖析

index.dat文件剖析

misterliwei

一.        前言

 

注重上网隐私和安全的人在每次上网后都会清除上网痕迹——“删除cookies”、“删除掉上网的临时缓存文件”以及“删除上网历史”。你觉得这样,所有的一切都会被擦除掉了。但是如果有人告诉你:这是不够的,系统中还有一些地方保存了你的上网信息,你是不是感到很恐慌?——这就是系统中的index.dat文件。

 

Windows系统中会存在三个index.dat文件。它们分别用来保存IE上网的cookies、临时文件和上网历史的索引信息(现在知道为什么这些文件名字是index.dat了吧J)。根据Windows系统版本不同,这些文件在系统中的位置也是不尽相同的。

 

Windows 95/98/Me/ NT中,index.dat一般会存放在下面的位置中:

C:/Windows/Cookies/index.dat
C:/Windows/History/History.IE5/index.dat
C:/Windows/Temporary Internet Files/Content.IE5/index.dat

而在Window2000/XP系统中,index.dat一般会存在于下面的位置中:

C:/Documents and Settings/<username>/Cookies/index.dat
C:/Documents and Settings/<username>/Local Settings/History/History.IE5/index.dat
C:/Documents and Settings/<username>/Local Settings

/Temporary Internet Files/Content.IE5/index.dat

这些index.dat文件是系统、隐藏的文件,它们不随IE浏览器中的cookies值、临时文件和历史记录的清除而删除——这就是它的可怕之处。下面来详细描述index.dat文件的结构。

 

二.        Index.dat文件结构

 

Index.dat文件分为两部分,头部分和条目(Entry)部分。

 

所谓头部分,顾名思义就是文件开始部分。它记录着这个文件的总的信息,如文件文件格式版本、大小、子文件夹等等。每个index.dat文件仅有一个头部分。

 

其余的部分都是条目部分。Index.dat中的各种类型的条目数据结构不同,不过每个条目的前8个字节结构相同,系统就是用这两个DWORD字段来区分条目类型的。

 

下面我们来具体分析一下各个部分:

 

1.  头部分

 

index.dat的头部大小是固定的,为16K。其开始592个字节(0x250)为小(SMALL)的头部分。紧接着的空间是3948DWORD,它用来作为分配MAP。数据结构如下:

 

struct CacheDir

{

   DWORD nFileCount;

   CHAR sDirName[8];

};

 

typedef struct _MEMMAP_HEADER_SMALL

{

TCHAR    FileSignature[28]; //”Client UrlCache MMF Ver 5.2”

    DWORD    FileSize;         //index.dat文件的大小

    DWORD    dwHashTableOffset;  //第一个哈希表的偏移

    DWORD    NumUrlInternalEntries;

    DWORD    NumUrlEntriesAlloced;

  // DWORD    dwGarbage; // 无效数据,只在/Zp8编译使用

    LONGLONG CacheLimit;

    LONGLONG CacheSize;

    LONGLONG ExemptUsage;

    DWORD    nDirCount;     //子目录个数

    CacheDir DirArray[32];     //子目录名称

    DWORD    dwHeaderData[33];

} MEMMAP_HEADER_SMALL;

 

typedef struct _MEMMAP_HEADER : _MEMMAP_HEADER_SMALL

{

    DWORD AllocationBitMap[3948];

} MEMMAP_HEADER, *LPMEMMAP_HEADER;

 

2.  各种条目结构

 

上文说过每个条目都是以同样结构的2DWORD开始的,这个结构如下:

 

 

typedef struct FILEMAP_ENTRY

{

    DWORD dwSig;  //条目标识

    DWORD nBlocks; //条目占用多少个快(128字节)

} *LPFILEMAP_ENTRY;

 

 

dwSig用来标识各种类型的标识。

 

表示字

说明

SIG_FREE

0xbadf00d

本条目空闲,只有此类条目没有nBlocks成员。

SIG_ALLOC

0xdeadbeef

已分配

SIG_URL

' LRU'

URL

SIG_REDIR

'RDER'

REDIR

SIG_LEAK

'KAEL'

LEAK

SIG_GLIST

'GLST'

GLIST

SIG_HASH

'HSAH'

哈希表

关于各种条目的结构我们下面会详细说明。

 

nBlocks用来描述此条目所占用的块数。注意index.dat中的块大小为128字节。

 

21哈希表条目

 

现在开始说明各种类型的条目。为什么先要说哈希表呢?这是因为index.dat使用一个哈希表链来作为目录,从而能够快速找到指定名称的条目。

 

Index.dat文件中每个哈希表大小都不能超过一个内存分页,即不能超过4K大小。每个哈希表部分是由下面的结构开始的,同时系统也是利用了这个结构,将index.dat中所有的哈希表部分链接起来的。

 

 

struct HASH_FILEMAP_ENTRY : FILEMAP_ENTRY

{

DWORD dwNext; // 下一个哈希表偏移(0表示为最后一个)

                  //偏移以index.dat文件第0字节为基地址。

    DWORD nBlock; // 本哈希表的序列号。从012…….

};

 

紧接着这个结构就是一个哈希表,每个哈希表的关键是哈希函数,下面是这个哈希表的哈希函数:

 

PRIVATE DWORD HashKey (LPCSTR lpsz)

{

    union

    {

        DWORD dw;

        BYTE c[4];

    }

    Hash, Hash2;

       

    const static BYTE bTranslate[256] =

    {

        1, 14,110, 25, 97,174,132,119,138,170,125,118, 27,233,140, 51,

        87,197,177,107,234,169, 56, 68, 30,  7,173, 73,188, 40, 36, 65,

        49,213,104,190, 57,211,148,223, 48,115, 15,  2, 67,186,210, 28,

        12,181,103, 70, 22, 58, 75, 78,183,167,238,157,124,147,172,144,

        176,161,141, 86, 60, 66,128, 83,156,241, 79, 46,168,198, 41,254,

        178, 85,253,237,250,154,133, 88, 35,206, 95,116,252,192, 54,221,

        102,218,255,240, 82,106,158,201, 61,  3, 89,  9, 42,155,159, 93,

        166, 80, 50, 34,175,195,100, 99, 26,150, 16,145,  4, 33,  8,189,

        121, 64, 77, 72,208,245,130,122,143, 55,105,134, 29,164,185,194,

        193,239,101,242,  5,171,126, 11, 74, 59,137,228,108,191,232,139,

        6, 24, 81, 20,127, 17, 91, 92,251,151,225,207, 21, 98,113,112,

        84,226, 18,214,199,187, 13, 32, 94,220,224,212,247,204,196, 43,

        249,236, 45,244,111,182,153,136,129, 90,217,202, 19,165,231, 71,

        230,142, 96,227, 62,179,246,114,162, 53,160,215,205,180, 47,109,

        44, 38, 31,149,135,  0,216, 52, 63, 23, 37, 69, 39,117,146,184,

        163,200,222,235,248,243,219, 10,152,131,123,229,203, 76,120,209

    };

 

    // Seed the hash values based on the first character.

    Hash.c[0] = bTranslate[ *lpsz];

    Hash.c[1] = bTranslate[(*lpsz+1) & 255];

    Hash.c[2] = bTranslate[(*lpsz+2) & 255];

    Hash.c[3] = bTranslate[(*lpsz+3) & 255];

 

    while (*++lpsz)

    {

        // Allow URLs differing only by trailing slash to collide.

        if (lpsz[0] == '/' && lpsz[1] == 0)

            break;

 

        Hash2.c[0] = Hash.c[0] ^ *lpsz;

        Hash2.c[1] = Hash.c[1] ^ *lpsz;

        Hash2.c[2] = Hash.c[2] ^ *lpsz;

        Hash2.c[3] = Hash.c[3] ^ *lpsz;

            

        Hash.c[0] = bTranslate[Hash2.c[0]];

        Hash.c[1] = bTranslate[Hash2.c[1]];

        Hash.c[2] = bTranslate[Hash2.c[2]];

        Hash.c[3] = bTranslate[Hash2.c[3]];

    }

    return Hash.dw;

}

经过这个函数产生的值,根据其低6位就是最终的数组行号(即相当于模64)。

 

由于解决冲突的方法是:对同一个哈希地址提供7个位置空间。于是呈现在我们眼前是实际上就是一个横向7列、纵向64行的表结构:

 

 

位置0

位置1

位置2

位置6

哈希地址0

 

 

 

 

 

1

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

63

 

 

 

 

 

 

从这样的表结构中,我们知道这个哈希表以64为模。每个表允许7个相同值,它们按顺序排列在一起。所以每个哈希表结构可以索引44864×7)个条目。

 

下面就是每个元素的结构:

 

struct HASH_ITEM

{

 DWORD dwHash;  //哈希值,注意最后6位为0

DWORD dwOffset; //指向的实体中的记录部分的偏移

                 //偏移以index.dat文件第0字节为基地址。

};

 

我们注意到了:数组元素的哈希值的低60。于是系统也是利用了这个特征,将这6位数用作了每个元素的格式表示:

 

#define HASH_BIT_NOTURL   0x0001  // 0

#define HASH_BIT_LOCK      0x0002  //1

#define HASH_BIT_REDIR     0x0004  //2

#define HASH_BIT_HASGRP   0x0008  //3

#define HASH_BIT_MULTGRP  0x0010  //4

#define HASH_BIT_RESERVED 0x0020  //5

 

// 上面的哈希值组合

#define HASH_UNLOCKED      0  // URL条目,没被锁定

#define HASH_FREE            1  // 空闲项,以前曾被使用过

#define HASH_LOCKED         2  // URL条目, 已锁定

#define HASH_END             3  // 空闲项,没被使用过

#define HASH_UNLOCKED_SLASH  4  // URL entry, not locked, trailing slash redir

#define HASH_REDIR           5  // redirect entry

#define HASH_LOCKED_SLASH   6  // URL entry, locked, trailing slash redir

#define HASH_FLAG_MASK       7  // illegal, used to mask out hash flags

 

2. 2 URL条目

 

URL条目是使用的最多的条目。它的结构和LEAK条目的结构相同,如下:

 

struct IE5_URL_FILEMAP_ENTRY : FILEMAP_ENTRY

{

    LONGLONG LastModifiedTime;       //最后修改时间

    LONGLONG LastAccessedTime;      //最后访问时间

    DWORD    dostExpireTime;         //到期时间

    DWORD    dostPostCheckTime;

 

    DWORD    dwFileSize;              //硬盘缓存中的文件的大小

    DWORD    dwRedirHashItemOffset;  // ask DanpoZ

    DWORD    dwGroupOffset;

    union

    {

        DWORD  dwExemptDelta;   // for SIG_URL

        DWORD  dwNextLeak;      // for SIG_LEAK

    };

   

    DWORD    CopySize;         // 好像总是0x60

    DWORD    UrlNameOffset;   // URL名称偏移。基地址是本URL条目的开始地址

    BYTE     DirIndex;           // 属于的子文件夹索引

    BYTE     bSyncState;        // automatic sync mode state

    BYTE     bVerCreate;        // 建立本ENTRYCACHE的版本

    BYTE     bVerUpdate;        // 升级本ENTRYCACHE的版本

       

DWORD    InternalFileNameOffset; //硬盘上文件名(不包括目录)字符串的偏移,

                                     //基地址是本URL条目的开始地址。

    DWORD    CacheEntryType;        //缓存类型

    DWORD    HeaderInfoOffset; //WEB服务器中取本文件时的返回的HTTP头部信息

    DWORD    HeaderInfoSize;  //和大小(注意包括最后的回车换行的)

    DWORD    FileExtensionOffset;    // should be WORD

    DWORD    dostLastSyncTime;      

    DWORD    NumAccessed;            // 存取次数(点击率)

    DWORD    NumReferences;          // 引用次数

    DWORD    dostFileCreationTime;   // 好像是ULONG

};

 

2. 4  REDIR结构:

 

struct REDIR_FILEMAP_ENTRY : FILEMAP_ENTRY

{

    DWORD dwItemOffset;  // offset to hash table item of destination URL

    DWORD dwHashValue;   // destination URL hash value (BUGBUG: collisions?)

    char  szUrl[4];      // original URL, can occupy more bytes

};

 

2. 5 GLIST结构:

 

struct LIST_FILEMAP_ENTRY : FILEMAP_ENTRY

{

    DWORD dwNext; // offset to next element in list

    DWORD nBlock; // sequence number for this block

};

 

三.        显示系统缓存信息

 

上面就是一个完整的index.dat文件的结构,利用这些结构我们就可以写出一个完整显示系统缓存信息的程序。这项非常琐碎的工作,于是微软专门提供了一个函数库——WinInet。利用这个库中的函数,程序员可以相当方便地取出系统中缓存中的信息。

 

关于WinInet库的使用方法网络上有很多文章,大家可以参阅。

 

1.  Exploring the URL Cache  http://www.codeproject.com/shell/urlexplr.asp

2.  Reading the Internet Explorer Cache http://www.codeproject.com/system/IECache.asp

 

四.        工作原理

 

上面我们分析了index.dat文件的结构,那么系统在什么时候读写这个文件的信息呢?

 

1.  COOKIES存取

 

在用户用IE浏览器上网时,当开始输入一个网址后,IE会根据输入的网址、用户名等信息组成一个字符串,将这个字符串作为参数到哈希函数中产生一个哈希值,然后查找具体的URL实体。如果能够找到,那么IE就会具体分析此URL实体指定的COOKIES.TXT文件,看是否已经过期,若已经过期则删除;否则将在IE生成的HTTP请求报文中加上一个cookies:××××××(×××就是.txt文件中的信息)这样的请求头部。

 

IE浏览器收到的HTTP响应报文中若响应头部中包含有Set-cookies:×××××信息时,此时IE就会将这个COOKIES值保存在一个.txt文件中,并在index.dat文件中建立一个索引值。

 

2.  临时的缓存文件存取

 

临时缓存文件是一种客户端缓存技术,它有利于节省网络带宽资源并能加快浏览速度。每次使用IE浏览器上网时,IE会发送一个请求报文要求传输一个文件(比如.htm文件、.jpg文件、.css文件等等)。WEB服务器响应请求,将所要求的文件传输给IE.IE在显示这个文件的同时,会将它放到缓存目录中,并在Index.dat文件中添加索引。

 

等下次,IE要求传输相同的文件时,IE便会在index.dat中找到这个文件的记录了(当然,如果根本没有传输下载过,index.dat中是不会找到这个记录的)。IE先检查这个文件是否已经过期了(WEB服务器会在响应某些文件请求时,在HTTP响应报文中添加一个响应头部Age:×××××来明确表示这个文件在客户机上保存的时间)。如果没有过期,IE便会直接利用这个缓冲文件而不会发送HTTP请求报文的。

 

如果没有明确的过期时间或者已经过期来,IE便会在发送的HTTP请求报文中加上一条请求头部If_modified-since:××××。而WEB服务器发现所要求的文件并没有改变,它便会发送一个304 Not Modified报文,而不再传输文件了。

 

3. 历史记录

 

历史记录只是用来保存曾经浏览过的网页的网址。它并不保存其他的一些信息。也不和发送/接受HTTP协议有关。所以比较简单。

 

五.             举例说明

 

理论说了很多,下面来举一个例子。通过这个例子我们看看系统是这样使用使用index.dat来索引缓存的以及系统是怎样使用缓存的。

 

1.  环境

 

一台装有WEB浏览器的客户机,一台IP地址为90.0.0.6IIS5WEB服务器。服务器有一个名为test.asp的网页。test.asp包含一张图,并会设置一个cookies

 

2.  第一次调用网页

 

过程如下图所示:

具体的HTTP报文如下:

 

请求报文

回应报文

GET /test.asp HTTP/1.1

Accept: image/gif, image/x-xbitmap, image/jpeg, image/pjpeg, application/x-shockwave-flash, application/vnd.ms-excel, application/vnd.ms-

powerpoint, application/msword, */*

Accept-Language: en

Accept-Encoding: gzip, deflate

User-Agent: Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1; SV1)

Host: 90.0.0.6

Connection: Keep-Alive

HTTP/1.1 200 OK

Server: Microsoft-IIS/5.0

Date: Thu, 26 Oct 2006 06:43:45 GMT

X-Powered-By: ASP.NET

Content-Length: 903

Content-Type: text/html

Set-Cookie: name=xiaoming; expires=Wed, 30-May-2007 16:00:00 GMT; path=/

Set-Cookie: ASPSESSIONIDASARBACA=NOMPFILDEICPMBJBKCDGKGDC; path=/

Cache-control: private

GET /img/1.gif HTTP/1.1

Accept: */*

Referer: http://90.0.0.6/test.asp

Accept-Language: en

Accept-Encoding: gzip, deflate

User-Agent: Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1; SV1)

Host: 90.0.0.6

Connection: Keep-Alive

Cookie: name=xiaoming; ASPSESSIONIDASARBACA=NOMPFILDEICPMBJBKCDGKGDC

HTTP/1.1 200 OK

Server: Microsoft-IIS/5.0

X-Powered-By: ASP.NET

Date: Thu, 26 Oct 2006 06:43:45 GMT

Content-Type: image/gif

Accept-Ranges: bytes

Last-Modified: Sun, 15 Oct 2006 15:54:58 GMT

ETag: "075bc 4372f 0c 61: 19f 8"

Content-Length: 66806

 

我们再来看一下,index.dat文件有什么变化呢?

1)临时缓存文件

 

首先我们计算1.gif文件的HASH值。URL名称为:http://90.0.0.6/img/1.gif ,经过上文的HashKey计算得出结果:0x 127F 5346。于是我们在第一个HASH表的0X5000 + 8 ×7 × 0x 127F 5346 & 0x 3F = 0x5150 开始查找:

 

 

00005150h: 01 00 00 00 00 9F 03 00 01 00 00 00 00 FD 03 00 ; .....?......?.

00005160h: 40 53 7F 12 80 66 00 00 40 E7 8F A7 80 F 2 01 00 ; @S.f..@?.

00005170h: C0 68 1D 59 80 1B 03 00 01 00 00 00 00 48 03 00 ; .Y........H..

00005180h: 01 00 00 00 00 6C 0E 00 01 00 00 00 00 93 03 00 ; .....l.......?.

00005190h: 01 00 00 00 00 B6 03 00 C 0 48 BE F4 00 D0 00    ; .....?.繦爵.?

 

 

发现5160h处就是我们要找的HASH_ITEM。于是我们在0X6680处找到我们要找的URL条目。

 

 

00006680h: 55 52 4C 20 03 00 00 00 00 75 BC 43 72 F 0 C 6 01 ; URL .....ur.

00006690h: 50 AC 0D 1D CC F 8 C 6 01 00 00 00 00 00 00 00 00 ; P?.?........

000066a 0h: F6 04 01 00 00 00 00 00 00 00 00 00 00 00 00 00 ; ?..............

000066b0h: 60 00 00 00 68 00 00 00 05 01 10 10 84 00 00 00 ; `...h.......?..

000066c 0h: 41 00 00 00 90 00 00 00 82 00 00 00 00 00 00 00 ; A...?..?......

000066d0h: 5A 35 49 37 02 00 00 00 00 00 00 00 5A 35 02 35 ; Z5I7........Z5.5

000066e0h: 00 00 00 00 0D F0 AD 0B 68 74 74 70 3A 2F 2F 39 ; ......http://9

000066f 0h: 30 2E 30 2E 30 2E 36 2F 69 6D 67 2F 31 2E 67 69 ; 0.0.0 .6/img/1.gi

00006700h: 66 00 AD 0B 31 5B 31 5D 2E 67 69 66 00 F 0 AD 0B ; f.?1[1].gif..

00006710h: 48 54 54 50 2F 31 2E 31 20 32 30 30 20 4F 4B 0D ; HTTP/1.1 200 OK.

00006720h: 0A 58 2D 50 6F 77 65 72 65 64 2D 42 79 3A 20 41 ; .X-Powered-By: A

00006730h: 53 50 2E 4E 45 54 0D 0A 43 6F 6E 74 65 6E 74 2D ; SP.NET..Content-

00006740h: 54 79 70 65 3A 20 69 6D 61 67 65 2F 67 69 66 0D ; Type: image/gif.

00006750h: 0A 45 54 61 67 3A 20 22 30 37 35 62 63 34 33 37 ; .ETag: "075bc437

00006760h: 32 66 30 63 36 31 3A 31 39 66 38 22 0D 0A 43 6F ; 2f 0c 61: 19f 8"..Co

00006770h: 6E 74 65 6E 74 2D 4C 65 6E 67 74 68 3A 20 36 36 ; ntent-Length: 66

00006780h: 38 30 36 0D 0A 0D 0A 7E 55 3A 71 67 6D 69 73 0D ; 806....~U:qgmis.

00006790h: 0A 00 AD 0B 0D F0 AD 0B 0D F0 AD 0B 0D F0 AD 0B ; ..?......

000067a 0h: 0D F0 AD 0B 0D F0 AD 0B 0D F0 AD 0B 0D F0 AD 0B ; ........

000067b0h: 0D F0 AD 0B 0D F0 AD 0B 0D F0 AD 0B 0D F0 AD 0B ; ........

000067c 0h: 0D F0 AD 0B 0D F0 AD 0B 0D F0 AD 0B 0D F0 AD 0B ; ........

000067d0h: 0D F0 AD 0B 0D F0 AD 0B 0D F0 AD 0B 0D F0 AD 0B ; ........

000067e0h: 0D F0 AD 0B 0D F0 AD 0B 0D F0 AD 0B 0D F0       ; .......

 

 

分析这个结构,FILEMAP_ENTRY分析如下:

 

地址

成员

说明

00006680h

dwSig

55 52 4C 20

URL

00006684h

nBlocks

02 00 00 00

此条目占据2×128256个字节

 

IE5_URL_FILEMAP_ENTRY分析如下:

 

地址

成员

说明

00006680h

LastModifiedTime

75 BC 43 72 F 0 C 6 01

最后修改时间: 2006-10-15

 115458 PM

 

LastAccessedTime

50 AC 0D 1D CC F 8 C 6 01

最后存取时间: 2006-10-26

 025817 PM

 

dostExpireTime

00 00 00 00

 

 

dostPostCheckTime

00 00 00 00

 

 

dwFileSize

F6 04 01 00

硬盘缓存的文件大小0x 104F 6

 

dwRedirHashItemOffset

00 00 00 00

 

 

dwGroupOffset

00 00 00 00

 

 

dwExemptDelta

00 00 00 00

 

 

CopySize

60 00 00 00

 

 

UrlNameOffset

68 00 00 00

URL地址保存在偏移为0X680X66E8的位置处。

http://90.0.0.6/img/1.gif

 

DirIndex

05

硬盘文件子目录序号为:05

 

bSyncState

01

 

 

bVerCreate

10

 

 

bVerUpdate

10

 

 

InternalFileNameOffset

84 00 00 00

硬盘缓存文件名保存在偏移为0X840X6704的位置处。

1[1].gif

 

CacheEntryType

41 30 00 00

 

 

HeaderInfoOffset

90 00 00 00

HTTP首部信息保存在偏移为0X900X6710的位置处。

HTTP/1.1 200 OK

X-Powered-By: ASP.NET

Content-Type: image/gif

ETag: "075bc 4372f 0c 61: 19f 8"

Content-Length: 66806

 

~U:qgmis

 

HeaderInfoSize

82 00 00 00

HTTP首部信息大小。

 

FileExtensionOffset

00 00 00 00

 

 

dostLastSyncTime

5A 35 49 37

最后同步时间为: 2006-10-26

 025818 PM

 

NumAccessed

02 00 00 00

存取3

 

NumReferences

00 00 00 00

 

 

dostFileCreationTime

5A 35 02 35

文件建立时间

 

我们用同样的方法分析test.aspindex.dat中保存成test[1].htm的索引信息。同样也可以分析cookiesindex.dat的索引信息。

 

经过了一次访问后,IE会将所有的访问过的文件放入缓存中,并在index.dat作索引。待第二次访问同样的网页时,将会出现什么情况呢?

 

3.  第二此调用网页

 

当我们再次浏览这个网页的时候。我们来看看发生了什么情况。

 

 

  下面是它们的HTTP报文信息。

请求报文

回应报文

GET /test.asp HTTP/1.1

Accept: image/gif, image/x-xbitmap, image/jpeg, image/pjpeg, application/x-shockwave-flash, application/vnd.ms-excel, application/vnd.ms-powerpoint, application/msword, */*

Accept-Language: en

Accept-Encoding: gzip, deflate

User-Agent: Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1; SV1)

Host: 90.0.0.6

Connection: Keep-Alive

Cookie: name=xiaoming

HTTP/1.1 200 OK

Server: Microsoft-IIS/5.0

Date: Thu, 26 Oct 2006 07:01:33 GMT

X-Powered-By: ASP.NET

Content-Length: 903

Content-Type: text/html

Set-Cookie: name=xiaoming; expires=Wed, 30-May-2007 16:00:00 GMT; path=/

Set-Cookie: ASPSESSIONIDASARBACA=OOMPFILDPDCEKPECJOOCPJEP; path=/

Cache-control: private

GET /img/1.gif HTTP/1.1

Accept: */*

Referer: http://90.0.0.6/test.asp

Accept-Language: en

Accept-Encoding: gzip, deflate

If-Modified-Since: Sun, 15 Oct 2006 15:54:58 GMT

If-None-Match: "075bc 4372f 0c 61: 19f 8"

User-Agent: Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1; SV1)

Host: 90.0.0.6

Connection: Keep-Alive

Cookie: name=xiaoming; ASPSESSIONIDASARBACA=OOMPFILDPDCEKPECJOOCPJEP

HTTP/1.1 304 Not Modified

Server: Microsoft-IIS/5.0

Date: Thu, 26 Oct 2006 07:01:33 GMT

X-Powered-By: ASP.NET

ETag: "075bc 4372f 0c 61: 19f 8"

Content-Length: 0

 

我们发现第二次访问时,1.gif文件根本不需要再次传输。因为服务器端这个文件根本没有变化过。于是IE就直接从index.dat索引文件中找到1.gif文件保存在硬盘上的位置后,就直接使用它了——这就是系统使用缓存的最终目的了。

4.  题外话

 

说说上面这些报文的一些题外话。

 

1)  每次请求一个ASP网页时,WEB服务器都会回应一个有ASPSEEIONID×××的cookies报文,ASP.DLL就是使用这个ASPSESSIONID来管理Session对象的——即使我们在asp文件中根本就没有使用这个对象。

 

2)  每次这个ASPSESSSIONID不会保存在硬盘上,它是存在IE浏览器的内存中,并且有时间期限。关闭IE或者过期后,将不会再在下次请求报文中包含这个ASPSESSIONID cookies值。于是WEB服务器又返回和一个原来不同的新的SESSIONID值。

 

 

六.        总结

本文主要剖析了Windows中用来索引缓存文件、cookies文件和上文记录的Index.dat文件,并给了例题。本文主要在分析微软代码的基础的得出的,但是对于index.dat文件中的一些结构中的特殊字段不能正确得出其含义,非常遗憾,希望有爱好者能完成。

 
  • 1
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 5
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值