46
46
CBDATA_CLASS_INIT(RebuildState);
49
class UFSSwapLogParser_old:public UFSSwapLogParser
52
struct StoreSwapLogDataOld {
62
unsigned char key[SQUID_MD5_DIGEST_LENGTH];
64
UFSSwapLogParser_old(FILE *fp):UFSSwapLogParser(fp) {
65
record_size = sizeof(UFSSwapLogParser_old::StoreSwapLogDataOld);
67
bool ReadRecord(StoreSwapLogData &swapData);
71
bool UFSSwapLogParser_old::ReadRecord(StoreSwapLogData &swapData)
73
UFSSwapLogParser_old::StoreSwapLogDataOld readData;
74
int bytes = sizeof(UFSSwapLogParser_old::StoreSwapLogDataOld);
78
if (fread(&readData, bytes, 1, log) != 1) {
81
swapData.op = readData.op;
82
swapData.swap_filen = readData.swap_filen;
83
swapData.timestamp = readData.timestamp;
84
swapData.lastref = readData.lastref;
85
swapData.expires = readData.expires;
86
swapData.lastmod = readData.lastmod;
87
swapData.swap_file_sz = readData.swap_file_sz;
88
swapData.refcount = readData.refcount;
89
swapData.flags = readData.flags;
90
xmemcpy(swapData.key, readData.key, SQUID_MD5_DIGEST_LENGTH);
48
/// Parse a swap header entry created on a system with 32-bit size_t and sfileno
49
/// this is typical of 32-bit systems without large file support
50
/// NP: SQUID_MD5_DIGEST_LENGTH is very risky still.
51
class UFSSwapLogParser_v1_32bs:public UFSSwapLogParser
54
/// version 1 cache swap.state entry with 32-bit size_t (swap_file_sz)
55
/// time_t an sfileno have no variation from the v1 baseline format
56
struct StoreSwapLogDataOld {
63
uint32_t swap_file_sz;
66
unsigned char key[SQUID_MD5_DIGEST_LENGTH];
68
UFSSwapLogParser_v1_32bs(FILE *fp):UFSSwapLogParser(fp) {
69
record_size = sizeof(UFSSwapLogParser_v1_32bs::StoreSwapLogDataOld);
71
/// Convert the on-disk 32-bit format to our current format while reading
72
bool ReadRecord(StoreSwapLogData &swapData) {
73
UFSSwapLogParser_v1_32bs::StoreSwapLogDataOld readData;
74
int bytes = sizeof(UFSSwapLogParser_v1_32bs::StoreSwapLogDataOld);
78
if (fread(&readData, bytes, 1, log) != 1) {
81
swapData.op = readData.op;
82
swapData.swap_filen = readData.swap_filen;
83
swapData.timestamp = readData.timestamp;
84
swapData.lastref = readData.lastref;
85
swapData.expires = readData.expires;
86
swapData.lastmod = readData.lastmod;
87
swapData.swap_file_sz = readData.swap_file_sz;
88
swapData.refcount = readData.refcount;
89
swapData.flags = readData.flags;
90
xmemcpy(swapData.key, readData.key, SQUID_MD5_DIGEST_LENGTH);
95
/// Parse a swap header entry created on a system with 32-bit size_t, time_t and sfileno
96
/// this is typical of 32-bit systems without large file support and with old kernels
97
/// NP: SQUID_MD5_DIGEST_LENGTH is very risky still.
98
class UFSSwapLogParser_v1_32bst:public UFSSwapLogParser
101
/// version 1 cache swap.state entry with 32-bit size_t (swap_file_sz)
102
/// time_t also differs
103
/// sfileno has no variation from the v1 baseline format
104
struct StoreSwapLogDataOld {
111
uint32_t swap_file_sz;
114
unsigned char key[SQUID_MD5_DIGEST_LENGTH];
116
UFSSwapLogParser_v1_32bst(FILE *fp):UFSSwapLogParser(fp) {
117
record_size = sizeof(UFSSwapLogParser_v1_32bst::StoreSwapLogDataOld);
119
/// Convert the on-disk 32-bit format to our current format while reading
120
bool ReadRecord(StoreSwapLogData &swapData) {
121
UFSSwapLogParser_v1_32bst::StoreSwapLogDataOld readData;
122
int bytes = sizeof(UFSSwapLogParser_v1_32bst::StoreSwapLogDataOld);
126
if (fread(&readData, bytes, 1, log) != 1) {
129
swapData.op = readData.op;
130
swapData.swap_filen = readData.swap_filen;
131
swapData.timestamp = readData.timestamp;
132
swapData.lastref = readData.lastref;
133
swapData.expires = readData.expires;
134
swapData.lastmod = readData.lastmod;
135
swapData.swap_file_sz = readData.swap_file_sz;
136
swapData.refcount = readData.refcount;
137
swapData.flags = readData.flags;
138
xmemcpy(swapData.key, readData.key, SQUID_MD5_DIGEST_LENGTH);
143
/// Parse a swap header entry created on a system with 64-bit size_t and sfileno
144
/// this is typical of 64-bit systems prior to this patch fixing sfileno to 32-bits
145
/// NP: SQUID_MD5_DIGEST_LENGTH is very risky still.
146
class UFSSwapLogParser_v1_64bfn:public UFSSwapLogParser
149
/// version 1 cache swap.state entry with 64-bit sfileno
150
struct StoreSwapLogDataOld {
157
uint64_t swap_file_sz;
160
unsigned char key[SQUID_MD5_DIGEST_LENGTH];
162
UFSSwapLogParser_v1_64bfn(FILE *fp):UFSSwapLogParser(fp) {
163
record_size = sizeof(UFSSwapLogParser_v1_64bfn::StoreSwapLogDataOld);
165
/// Convert the on-disk 64-bit format to our current format while reading
166
bool ReadRecord(StoreSwapLogData &swapData) {
167
UFSSwapLogParser_v1_64bfn::StoreSwapLogDataOld readData;
168
int bytes = sizeof(UFSSwapLogParser_v1_64bfn::StoreSwapLogDataOld);
172
if (fread(&readData, bytes, 1, log) != 1) {
175
swapData.op = readData.op;
176
if ((readData.swap_filen>>32) != 0) {
177
fatalf("File ID on record is greater than maximum cache file ID.");
179
swapData.swap_filen = (int32_t)readData.swap_filen;
180
swapData.timestamp = readData.timestamp;
181
swapData.lastref = readData.lastref;
182
swapData.expires = readData.expires;
183
swapData.lastmod = readData.lastmod;
184
swapData.swap_file_sz = readData.swap_file_sz;
185
swapData.refcount = readData.refcount;
186
swapData.flags = readData.flags;
187
xmemcpy(swapData.key, readData.key, SQUID_MD5_DIGEST_LENGTH);
95
192
class UFSSwapLogParser_v1:public UFSSwapLogParser
127
224
if (header.op != SWAP_LOG_VERSION) {
128
debugs(47, 1, "Old swap file detected... ");
225
debugs(47, 1, "Old swap file detected...");
129
226
fseek(fp, 0, SEEK_SET);
130
return new UFSSwapLogParser_old(fp);
227
return new UFSSwapLogParser_v1_32bs(fp); // Um. 32-bits except time_t, and can't determine that.
133
230
if (header.version == 1) {
134
231
if (fseek(fp, header.record_size, SEEK_SET) != 0)
137
if (header.record_size == sizeof(struct UFSSwapLogParser_old::StoreSwapLogDataOld)) {
138
debugs(47, 1, "Version 1 of swap file without LFS support detected... ");
139
return new UFSSwapLogParser_old(fp);
236
// native time_t (hopefully 64-bit)
142
238
if (header.record_size == sizeof(StoreSwapLogData)) {
143
239
debugs(47, 1, "Version 1 of swap file with LFS support detected... ");
144
240
return new UFSSwapLogParser_v1(fp);
147
debugs(47, 1, "The swap file has wrong format!... ");
243
// which means we have a 3-way grid of permutations to import (yuck!)
244
// 1) sfileno 32-bit / 64-bit (64-bit was broken)
245
// 2) time_t 32-bit / 64-bit
246
// 3) size_t 32-bit / 64-bit (32-bit was pre-LFS)
249
// only LFS (size_t) differs from baseline
250
if (header.record_size == sizeof(struct UFSSwapLogParser_v1_32bs::StoreSwapLogDataOld)) {
251
debugs(47, 1, "Version 1 (32-bit) swap file without LFS support detected... ");
252
return new UFSSwapLogParser_v1_32bs(fp);
254
// LFS (size_t) and timestamps (time_t) differs from baseline
255
if (header.record_size == sizeof(struct UFSSwapLogParser_v1_32bst::StoreSwapLogDataOld)) {
256
debugs(47, 1, "Version 1 (32-bit) swap file with short timestamps and without LFS support detected... ");
257
return new UFSSwapLogParser_v1_32bst(fp);
259
// No downgrade for 64-bit timestamps to 32-bit.
262
// sfileno was 64-bit for a some builds
263
if (header.record_size == sizeof(struct UFSSwapLogParser_v1_64bfn::StoreSwapLogDataOld)) {
264
debugs(47, 1, "Version 1 (64-bit) swap file with broken sfileno detected... ");
265
return new UFSSwapLogParser_v1_64bfn(fp);
267
// NP: 64-bit system with 32-bit size_t/time_t are not handled.
269
debugs(47, 1, "WARNING: The swap file has wrong format!... ");
270
debugs(47, 1, "NOTE: Cannot safely downgrade caches to short (32-bit) timestamps.");
274
// XXX: version 2 of swapfile. This time use fixed-bit sizes for everything!!
275
// and preferrably write to disk in network-order bytes for the larger fields.