3
A brief file description
5
@section license License
7
Licensed to the Apache Software Foundation (ASF) under one
8
or more contributor license agreements. See the NOTICE file
9
distributed with this work for additional information
10
regarding copyright ownership. The ASF licenses this file
11
to you under the Apache License, Version 2.0 (the
12
"License"); you may not use this file except in compliance
13
with the License. You may obtain a copy of the License at
15
http://www.apache.org/licenses/LICENSE-2.0
17
Unless required by applicable law or agreed to in writing, software
18
distributed under the License is distributed on an "AS IS" BASIS,
19
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
20
See the License for the specific language governing permissions and
21
limitations under the License.
29
struct ShowCacheInternal: public ShowCont
33
CacheKey show_cache_key;
37
int showMain(int event, Event * e);
38
int showEvacuations(int event, Event * e);
39
int showPartEvacuations(int event, Event * e);
40
int showPartitions(int event, Event * e);
41
int showPartPartitions(int event, Event * e);
42
int showSegments(int event, Event * e);
43
int showSegSegment(int event, Event * e);
44
#ifdef CACHE_STAT_PAGES
45
int showConnections(int event, Event * e);
46
int showPartConnections(int event, Event * e);
49
ShowCacheInternal(Continuation * c, HTTPHdr * h):ShowCont(c, h), part_index(0), seg_index(0)
51
SET_HANDLER(&ShowCacheInternal::showMain);
54
~ShowCacheInternal() {
58
extern ShowCacheInternal *theshowcacheInternal;
59
Action *register_ShowCacheInternal(Continuation * c, HTTPHdr * h);
65
extern volatile int gnpart;
69
ShowCacheInternal *theshowcacheInternal = NULL;
72
#define STREQ_PREFIX(_x,_s) (!strncasecmp(_x,_s,sizeof(_s)-1))
73
#define STREQ_LEN_PREFIX(_x,_l,_s) (path_len < sizeof(_s) && !strncasecmp(_x,_s,sizeof(_s)-1))
77
register_ShowCacheInternal(Continuation * c, HTTPHdr * h)
79
theshowcacheInternal = NEW(new ShowCacheInternal(c, h));
80
URL *u = h->url_get();
83
const char *path = u->path_get(&path_len);
87
#ifdef CACHE_STAT_PAGES
88
else if (STREQ_LEN_PREFIX(path, path_len, "connections")) {
89
SET_CONTINUATION_HANDLER(theshowcacheInternal, &ShowCacheInternal::showConnections);
92
else if (STREQ_PREFIX(path, "evacuations")) {
93
SET_CONTINUATION_HANDLER(theshowcacheInternal, &ShowCacheInternal::showEvacuations);
94
} else if (STREQ_PREFIX(path, "partitions")) {
95
SET_CONTINUATION_HANDLER(theshowcacheInternal, &ShowCacheInternal::showPartitions);
98
if (theshowcacheInternal->mutex->thread_holding)
99
CONT_SCHED_LOCK_RETRY(theshowcacheInternal);
101
eventProcessor.schedule_imm(theshowcacheInternal, ET_NET);
102
return &theshowcacheInternal->action;
107
ShowCacheInternal::showMain(int event, Event * e)
109
CHECK_SHOW(begin("Cache"));
110
#ifdef CACHE_STAT_PAGES
111
CHECK_SHOW(show("<H3>Show <A HREF=\"./connections\">Connections</A></H3>\n"
112
"<H3>Show <A HREF=\"./evacuations\">Evacuations</A></H3>\n"
113
"<H3>Show <A HREF=\"./partitions\">Partitions</A></H3>\n"));
115
CHECK_SHOW(show("<H3>Show <A HREF=\"./evacuations\">Evacuations</A></H3>\n"
116
"<H3>Show <A HREF=\"./partitions\">Partitions</A></H3>\n"));
118
return complete(event, e);
121
#ifdef CACHE_STAT_PAGES
123
ShowCacheInternal::showConnections(int event, Event * e)
125
CHECK_SHOW(begin("Cache VConnections"));
126
CHECK_SHOW(show("<H3>Cache Connections</H3>\n"
127
"<table border=1><tr>"
130
"<th>URL/Hash</th>" "<th>Bytes Done</th>" "<th>Total Bytes</th>" "<th>Bytes Todo</th>" "</tr>\n"));
132
SET_HANDLER(&ShowCacheInternal::showPartConnections);
133
CONT_SCHED_LOCK_RETRY_RET(this);
138
ShowCacheInternal::showPartConnections(int event, Event * e)
140
CACHE_TRY_LOCK(lock, gpart[part_index]->mutex, mutex->thread_holding);
142
CONT_SCHED_LOCK_RETRY_RET(this);
144
for (CacheVC * vc = (CacheVC *) gpart[part_index]->stat_cache_vcs.head; vc; vc = vc->stat_link.next) {
146
char nbytes[60], todo[60], url[81092];
150
MUTEX_LOCK(lock2, vc->mutex, mutex->thread_holding);
151
// if vc is closed ignore - Ramki 08/30/2000
154
sprintf(nbytes, "%d", vc->vio.nbytes);
155
sprintf(todo, "%d", vc->vio.ntodo());
157
if (vc->f.frag_type == CACHE_FRAG_TYPE_HTTP && vc->request.valid()) {
158
URL *u = vc->request.url_get(&uu);
159
u->print(url, 8000, &ib, &xd);
161
} else if (vc->alternate.valid()) {
162
URL *u = vc->alternate.request_url_get(&uu);
163
u->print(url, 8000, &ib, &xd);
167
CHECK_SHOW(show("<tr>" "<td>%s</td>" // operation
168
"<td>%s</td>" // Part
169
"<td>%s</td>" // URL/Hash
174
((vc->vio.op == VIO::READ) ? "Read" : "Write"),
178
vc->vio.nbytes == INT64_MAX ? "all" : nbytes, vc->vio.nbytes == INT64_MAX ? "all" : todo));
181
if (part_index < gnpart)
182
CONT_SCHED_LOCK_RETRY(this);
184
CHECK_SHOW(show("</table>\n"));
185
return complete(event, e);
194
ShowCacheInternal::showEvacuations(int event, Event * e)
196
CHECK_SHOW(begin("Cache Pending Evacuations"));
197
CHECK_SHOW(show("<H3>Cache Evacuations</H3>\n"
198
"<table border=1><tr>"
199
"<th>Offset</th>" "<th>Estimated Size</th>" "<th>Reader Count</th>" "<th>Done</th>" "</tr>\n"));
201
SET_HANDLER(&ShowCacheInternal::showPartEvacuations);
202
CONT_SCHED_LOCK_RETRY_RET(this);
207
ShowCacheInternal::showPartEvacuations(int event, Event * e)
209
Part *p = gpart[part_index];
210
CACHE_TRY_LOCK(lock, p->mutex, mutex->thread_holding);
212
CONT_SCHED_LOCK_RETRY_RET(this);
215
int last = (p->len - (p->start - p->skip)) / EVACUATION_BUCKET_SIZE;
216
for (int i = 0; i < last; i++) {
217
for (b = p->evacuate[i].head; b; b = b->link.next) {
219
sprintf(offset, "%" PRIu64 "", (uint64_t) part_offset(p, &b->dir));
220
CHECK_SHOW(show("<tr>" "<td>%s</td>" // offset
221
"<td>%d</td>" // estimated size
222
"<td>%d</td>" // reader count
223
"<td>%s</td>" // done
224
"</tr>\n", offset, (int) dir_approx_size(&b->dir), b->readers, b->f.done ? "yes" : "no"));
228
if (part_index < gnpart)
229
CONT_SCHED_LOCK_RETRY(this);
231
CHECK_SHOW(show("</table>\n"));
232
return complete(event, e);
238
ShowCacheInternal::showPartitions(int event, Event * e)
240
CHECK_SHOW(begin("Cache Partitions"));
241
CHECK_SHOW(show("<H3>Cache Partitions</H3>\n"
242
"<table border=1><tr>"
245
"<th>Directory Entries</th>"
246
"<th>Write Position</th>"
247
"<th>Write Agg Todo</th>"
248
"<th>Write Agg Todo Size</th>"
249
"<th>Write Agg Done</th>"
250
"<th>Phase</th>" "<th>Create Time</th>" "<th>Sync Serial</th>" "<th>Write Serial</th>" "</tr>\n"));
252
SET_HANDLER(&ShowCacheInternal::showPartPartitions);
253
CONT_SCHED_LOCK_RETRY_RET(this);
258
ShowCacheInternal::showPartPartitions(int event, Event * e)
260
Part *p = gpart[part_index];
261
CACHE_TRY_LOCK(lock, p->mutex, mutex->thread_holding);
263
CONT_SCHED_LOCK_RETRY_RET(this);
266
ink_ctime_r(&p->header->create_time, ctime);
267
ctime[strlen(ctime) - 1] = 0;
269
int agg_done = p->agg_buf_pos;
271
for (c = p->agg.head; c; c = (CacheVC *) c->link.next)
273
CHECK_SHOW(show("<tr>" "<td>%s</td>" // ID
274
"<td>%" PRId64 "</td>" // blocks
275
"<td>%" PRId64 "</td>" // directory entries
276
"<td>%" PRId64 "</td>" // write position
277
"<td>%d</td>" // write agg to do
278
"<td>%d</td>" // write agg to do size
279
"<td>%d</td>" // write agg done
280
"<td>%d</td>" // phase
281
"<td>%s</td>" // create time
282
"<td>%u</td>" // sync serial
283
"<td>%u</td>" // write serial
286
(uint64_t)((p->len - (p->start - p->skip)) / CACHE_BLOCK_SIZE),
287
(uint64_t)(p->buckets * DIR_DEPTH * p->segments),
288
(uint64_t)((p->header->write_pos - p->start) / CACHE_BLOCK_SIZE),
291
agg_done, p->header->phase, ctime, p->header->sync_serial, p->header->write_serial));
292
CHECK_SHOW(show("</table>\n"));
293
SET_HANDLER(&ShowCacheInternal::showSegments);
294
return showSegments(event, e);
298
ShowCacheInternal::showSegments(int event, Event * e)
300
CHECK_SHOW(show("<H3>Cache Partition Segments</H3>\n"
301
"<table border=1><tr>"
304
"<th>Empty</th>" "<th>Valid</th>" "<th>Agg Valid</th>" "<th>Avg Size</th>" "</tr>\n"));
306
SET_HANDLER(&ShowCacheInternal::showSegSegment);
308
CONT_SCHED_LOCK_RETRY_RET(this);
312
ShowCacheInternal::showSegSegment(int event, Event * e)
314
Part *p = gpart[part_index];
315
CACHE_TRY_LOCK(lock, p->mutex, mutex->thread_holding);
317
CONT_SCHED_LOCK_RETRY_RET(this);
318
int free = 0, used = 0, empty = 0, valid = 0, agg_valid = 0, avg_size = 0;
319
dir_segment_accounted(seg_index, p, 0, &free, &used, &empty, &valid, &agg_valid, &avg_size);
320
CHECK_SHOW(show("<tr>"
324
"<td>%d</td>" "<td>%d</td>" "<td>%d</td>" "</tr>\n", free, used, empty, valid, agg_valid, avg_size));
326
if (seg_index < p->segments)
327
CONT_SCHED_LOCK_RETRY(this);
329
CHECK_SHOW(show("</table>\n"));
332
if (part_index < gnpart)
333
CONT_SCHED_LOCK_RETRY(this);
335
return complete(event, e);
342
#endif // NON_MODULAR