XRootD
XrdPfcConfiguration.cc
Go to the documentation of this file.
1 #include "XrdPfc.hh"
2 #include "XrdPfcTrace.hh"
3 #include "XrdPfcInfo.hh"
4 
6 #include "XrdPfcPurgePin.hh"
7 
8 #include "XrdOss/XrdOss.hh"
9 
10 #include "XrdOuc/XrdOucEnv.hh"
11 #include "XrdOuc/XrdOucUtils.hh"
12 #include "XrdOuc/XrdOucStream.hh"
14 #include "XrdOuc/XrdOuca2x.hh"
15 
16 #include "XrdVersion.hh"
17 #include "XrdOfs/XrdOfsConfigPI.hh"
18 #include "XrdSys/XrdSysXAttr.hh"
19 
20 #include <fcntl.h>
21 
23 
24 namespace XrdPfc
25 {
26  const char *trace_what_strings[] = {"","error ","warning ","info ","debug ","dump "};
27 }
28 
29 using namespace XrdPfc;
30 
32 
34  m_write_through(false),
35  m_hdfsmode(false),
36  m_allow_xrdpfc_command(false),
37  m_data_space("public"),
38  m_meta_space("public"),
39  m_diskTotalSpace(-1),
40  m_diskUsageLWM(-1),
41  m_diskUsageHWM(-1),
42  m_fileUsageBaseline(-1),
43  m_fileUsageNominal(-1),
44  m_fileUsageMax(-1),
45  m_purgeInterval(300),
46  m_purgeColdFilesAge(-1),
47  m_purgeAgeBasedPeriod(10),
48  m_accHistorySize(20),
49  m_dirStatsInterval(900),
50  m_dirStatsStoreDepth(1),
51  m_bufferSize(128*1024),
52  m_RamAbsAvailable(0),
53  m_RamKeepStdBlocks(0),
54  m_wqueue_blocks(16),
55  m_wqueue_threads(4),
56  m_prefetch_max_blocks(10),
57  m_hdfsbsize(128*1024*1024),
58  m_flushCnt(2000),
59  m_cs_UVKeep(-1),
60  m_cs_Chk(CSChk_Net),
61  m_cs_ChkTLS(false),
62  m_onlyIfCachedMinSize(1024*1024),
63  m_onlyIfCachedMinFrac(1.0)
64 {}
65 
66 
67 bool Cache::cfg2bytes(const std::string &str, long long &store, long long totalSpace, const char *name) const
68 {
69  char errStr[1024];
70  snprintf(errStr, 1024, "ConfigParameters() Error parsing parameter %s", name);
71 
72  if (::isalpha(*(str.rbegin())))
73  {
74  if (XrdOuca2x::a2sz(m_log, errStr, str.c_str(), &store, 0, totalSpace))
75  {
76  return false;
77  }
78  }
79  else
80  {
81  char *eP;
82  errno = 0;
83  double frac = strtod(str.c_str(), &eP);
84  if (errno || eP == str.c_str())
85  {
86  m_log.Emsg(errStr, str.c_str());
87  return false;
88  }
89 
90  store = static_cast<long long>(totalSpace * frac + 0.5);
91  }
92 
93  if (store < 0 || store > totalSpace)
94  {
95  snprintf(errStr, 1024, "ConfigParameters() Error: parameter %s should be between 0 and total available disk space (%lld) - it is %lld (given as %s)",
96  name, totalSpace, store, str.c_str());
97  m_log.Emsg(errStr, "");
98  return false;
99  }
100 
101  return true;
102 }
103 
104 bool Cache::blocksize_str2value(const char *from, const char *str,
105  long long &val, long long min, long long max) const
106 {
107  if (XrdOuca2x::a2sz(m_log, "Error parsing block-size", str, &val, min, max))
108  return false;
109 
110  if (val & 0xFFF) {
111  val &= ~0x0FFF;
112  val += 0x1000;
113  m_log.Emsg(from, "blocksize must be a multiple of 4 kB. Rounded up.");
114  }
115 
116  return true;
117 }
118 
119 bool Cache::prefetch_str2value(const char *from, const char *str,
120  int &val, int min, int max) const
121 {
122  if (XrdOuca2x::a2i(m_log, "Error parsing prefetch block count", str, &val, min, max))
123  return false;
124 
125  return true;
126 }
127 
128 /* Function: xcschk
129 
130  Purpose: To parse the directive: cschk <parms>
131 
132  parms: [[no]net] [[no]tls] [[no]cache] [uvkeep <arg>]
133 
134  all Checksum check on cache & net transfers.
135  cache Checksum check on cache only, 'no' turns it off.
136  net Checksum check on net transfers 'no' turns it off.
137  tls use TLS if server doesn't support checksums 'no' turns it off.
138  uvkeep Maximum amount of time a cached file make be kept if it
139  contains unverified checksums as n[d|h|m|s], where 'n'
140  is a non-negative integer. A value of 0 prohibits disk
141  caching unless the checksum can be verified. You can
142  also specify "lru" which means the standard purge policy
143  is to be used.
144 
145  Output: true upon success or false upon failure.
146  */
147 bool Cache::xcschk(XrdOucStream &Config)
148 {
149  const char *val, *val2;
150  struct cschkopts {const char *opname; int opval;} csopts[] =
151  {
152  {"off", CSChk_None},
153  {"cache", CSChk_Cache},
154  {"net", CSChk_Net},
155  {"tls", CSChk_TLS}
156  };
157  int i, numopts = sizeof(csopts)/sizeof(struct cschkopts);
158  bool isNo;
159 
160  if (! (val = Config.GetWord()))
161  {m_log.Emsg("Config", "cschk parameter not specified"); return false; }
162 
163  while(val)
164  {
165  if ((isNo = strncmp(val, "no", 2) == 0))
166  val2 = val + 2;
167  else
168  val2 = val;
169  for (i = 0; i < numopts; i++)
170  {
171  if (!strcmp(val2, csopts[i].opname))
172  {
173  if (isNo)
174  m_configuration.m_cs_Chk &= ~csopts[i].opval;
175  else if (csopts[i].opval)
176  m_configuration.m_cs_Chk |= csopts[i].opval;
177  else
178  m_configuration.m_cs_Chk = csopts[i].opval;
179  break;
180  }
181  }
182  if (i >= numopts)
183  {
184  if (strcmp(val, "uvkeep"))
185  {
186  m_log.Emsg("Config", "invalid cschk option -", val);
187  return false;
188  }
189  if (!(val = Config.GetWord()))
190  {
191  m_log.Emsg("Config", "cschk uvkeep value not specified");
192  return false;
193  }
194  if (!strcmp(val, "lru"))
195  m_configuration.m_cs_UVKeep = -1;
196  else
197  {
198  int uvkeep;
199  if (XrdOuca2x::a2tm(m_log, "uvkeep time", val, &uvkeep, 0))
200  return false;
201  m_configuration.m_cs_UVKeep = uvkeep;
202  }
203  }
204  val = Config.GetWord();
205  }
206  // Decompose into separate TLS state, it is only passed on to psx
207  m_configuration.m_cs_ChkTLS = m_configuration.m_cs_Chk & CSChk_TLS;
208  m_configuration.m_cs_Chk &= ~CSChk_TLS;
209 
210  m_env->Put("psx.CSNet", m_configuration.is_cschk_net() ? (m_configuration.m_cs_ChkTLS ? "2" : "1") : "0");
211 
212  return true;
213 }
214 
215 
216 /* Function: xdlib
217 
218  Purpose: To parse the directive: decisionlib <path> [<parms>]
219 
220  <path> the path of the decision library to be used.
221  <parms> optional parameters to be passed.
222 
223 
224  Output: true upon success or false upon failure.
225  */
226 bool Cache::xdlib(XrdOucStream &Config)
227 {
228  const char* val;
229 
230  std::string libp;
231  if (! (val = Config.GetWord()) || ! val[0])
232  {
233  TRACE(Info," Cache::Config() decisionlib not specified; always caching files");
234  return true;
235  }
236  else
237  {
238  libp = val;
239  }
240 
241  char params[4096];
242  if (val[0])
243  Config.GetRest(params, 4096);
244  else
245  params[0] = 0;
246 
247  XrdOucPinLoader* myLib = new XrdOucPinLoader(&m_log, 0, "decisionlib",
248  libp.c_str());
249 
250  Decision *(*ep)(XrdSysError&);
251  ep = (Decision *(*)(XrdSysError&))myLib->Resolve("XrdPfcGetDecision");
252  if (! ep) {myLib->Unload(true); return false; }
253 
254  Decision * d = ep(m_log);
255  if (! d)
256  {
257  TRACE(Error, "Config() decisionlib was not able to create a decision object");
258  return false;
259  }
260  if (params[0])
261  d->ConfigDecision(params);
262 
263  m_decisionpoints.push_back(d);
264  return true;
265 }
266 
267 /* Function: xplib
268 
269  Purpose: To parse the directive: purgelib <path> [<parms>]
270 
271  <path> the path of the decision library to be used.
272  <parms> optional parameters to be passed.
273 
274 
275  Output: true upon success or false upon failure.
276  */
277 bool Cache::xplib(XrdOucStream &Config)
278 {
279  const char* val;
280 
281  std::string libp;
282  if (! (val = Config.GetWord()) || ! val[0])
283  {
284  TRACE(Info," Cache::Config() purgelib not specified; will use LRU for purging files");
285  return true;
286  }
287  else
288  {
289  libp = val;
290  }
291 
292  char params[4096];
293  if (val[0])
294  Config.GetRest(params, 4096);
295  else
296  params[0] = 0;
297 
298  XrdOucPinLoader* myLib = new XrdOucPinLoader(&m_log, 0, "purgelib",
299  libp.c_str());
300 
301  PurgePin *(*ep)(XrdSysError&);
302  ep = (PurgePin *(*)(XrdSysError&))myLib->Resolve("XrdPfcGetPurgePin");
303  if (! ep) {myLib->Unload(true); return false; }
304 
305  PurgePin * dp = ep(m_log);
306  if (! dp)
307  {
308  TRACE(Error, "Config() purgelib was not able to create a Purge Plugin object?");
309  return false;
310  }
311  m_purge_pin = dp;
312 
313  if (params[0])
314  m_purge_pin->ConfigPurgePin(params);
315 
316 
317  return true;
318 }
319 
320 /* Function: xtrace
321 
322  Purpose: To parse the directive: trace <level>
323  Output: true upon success or false upon failure.
324  */
325 bool Cache::xtrace(XrdOucStream &Config)
326 {
327  char *val;
328  static struct traceopts {const char *opname; int opval; } tropts[] =
329  {
330  {"none", 0},
331  {"error", 1},
332  {"warning", 2},
333  {"info", 3},
334  {"debug", 4},
335  {"dump", 5},
336  {"dumpxl", 6}
337  };
338  int numopts = sizeof(tropts)/sizeof(struct traceopts);
339 
340  if (! (val = Config.GetWord()))
341  {m_log.Emsg("Config", "trace option not specified"); return 1; }
342 
343  for (int i = 0; i < numopts; i++)
344  {
345  if (! strcmp(val, tropts[i].opname))
346  {
347  m_trace->What = tropts[i].opval;
348  return true;
349  }
350  }
351  m_log.Emsg("Config", "invalid trace option -", val);
352  return false;
353 }
354 
355 // Determine if oss spaces are operational and if they support xattrs.
356 bool Cache::test_oss_basics_and_features()
357 {
358  static const char *epfx = "test_oss_basics_and_features()";
359 
360  const auto &conf = m_configuration;
361  const char *user = conf.m_username.c_str();
362  XrdOucEnv env;
363 
364  auto check_space = [&](const char *space, bool &has_xattr)
365  {
366  std::string fname("__prerun_test_pfc_");
367  fname += space;
368  fname += "_space__";
369  env.Put("oss.cgroup", space);
370 
371  int res = m_oss->Create(user, fname.c_str(), 0600, env, XRDOSS_mkpath);
372  if (res != XrdOssOK) {
373  m_log.Emsg(epfx, "Can not create a file on space", space);
374  return false;
375  }
376  XrdOssDF *oss_file = m_oss->newFile(user);
377  res = oss_file->Open(fname.c_str(), O_RDWR, 0600, env);
378  if (res != XrdOssOK) {
379  m_log.Emsg(epfx, "Can not open a file on space", space);
380  return false;
381  }
382  res = oss_file->Write(fname.data(), 0, fname.length());
383  if (res != (int) fname.length()) {
384  m_log.Emsg(epfx, "Can not write into a file on space", space);
385  return false;
386  }
387 
388  has_xattr = true;
389  long long fsize = fname.length();
390  res = XrdSysXAttrActive->Set("pfc.fsize", &fsize, sizeof(long long), 0, oss_file->getFD(), 0);
391  if (res != 0) {
392  m_log.Emsg(epfx, "Can not write xattr to a file on space", space);
393  has_xattr = false;
394  }
395 
396  oss_file->Close();
397 
398  if (has_xattr) {
399  char pfn[4096];
400  m_oss->Lfn2Pfn(fname.c_str(), pfn, 4096);
401  fsize = -1ll;
402  res = XrdSysXAttrActive->Get("pfc.fsize", &fsize, sizeof(long long), pfn);
403  if (res != sizeof(long long) || fsize != (long long) fname.length())
404  {
405  m_log.Emsg(epfx, "Can not read xattr from a file on space", space);
406  has_xattr = false;
407  }
408  }
409 
410  res = m_oss->Unlink(fname.c_str());
411  if (res != XrdOssOK) {
412  m_log.Emsg(epfx, "Can not unlink a file on space", space);
413  return false;
414  }
415 
416  return true;
417  };
418 
419  bool aOK = true;
420  aOK &= check_space(conf.m_data_space.c_str(), m_dataXattr);
421  aOK &= check_space(conf.m_meta_space.c_str(), m_metaXattr);
422 
423  return aOK;
424 }
425 
426 //______________________________________________________________________________
427 /* Function: Config
428 
429  Purpose: To parse configuration file and configure Cache instance.
430  Output: true upon success or false upon failure.
431  */
432 bool Cache::Config(const char *config_filename, const char *parameters, XrdOucEnv *env)
433 {
434  // Indicate whether or not we are a client instance
435  const char *theINS = getenv("XRDINSTANCE");
436  m_isClient = (theINS != 0 && strncmp("*client ", theINS, 8) == 0);
437 
438  // Tell everyone else we are a caching proxy
439  XrdOucEnv::Export("XRDPFC", 1);
440 
441  XrdOucEnv emptyEnv;
442  XrdOucEnv *myEnv = env ? env : &emptyEnv;
443 
444  XrdOucStream Config(&m_log, theINS, myEnv, "=====> ");
445 
446  if (! config_filename || ! *config_filename)
447  {
448  TRACE(Error, "Config() configuration file not specified.");
449  return false;
450  }
451 
452  int fd;
453  if ( (fd = open(config_filename, O_RDONLY, 0)) < 0)
454  {
455  TRACE( Error, "Config() can't open configuration file " << config_filename);
456  return false;
457  }
458 
459  Config.Attach(fd);
460  static const char *cvec[] = { "*** pfc plugin config:", 0 };
461  Config.Capture(cvec);
462 
463  // Obtain OFS configurator for OSS plugin.
464  XrdOfsConfigPI *ofsCfg = XrdOfsConfigPI::New(config_filename,&Config,&m_log,
465  &XrdVERSIONINFOVAR(XrdOucGetCache));
466  if (! ofsCfg) return false;
467 
468  TmpConfiguration tmpc;
469 
470  Configuration &CFG = m_configuration;
471 
472  // Adjust default parameters for client/serverless caching
473  if (m_isClient)
474  {
475  m_configuration.m_bufferSize = 128 * 1024; // same as normal.
476  m_configuration.m_wqueue_blocks = 8;
477  m_configuration.m_wqueue_threads = 1;
478  }
479 
480  // If network checksum processing is the default, indicate so.
481  if (m_configuration.is_cschk_net()) m_env->Put("psx.CSNet", m_configuration.m_cs_ChkTLS ? "2" : "1");
482 
483  // Actual parsing of the config file.
484  bool retval = true, aOK = true;
485  char *var;
486  while ((var = Config.GetMyFirstWord()))
487  {
488  if (! strcmp(var,"pfc.osslib"))
489  {
490  retval = ofsCfg->Parse(XrdOfsConfigPI::theOssLib);
491  }
492  else if (! strcmp(var,"pfc.cschk"))
493  {
494  retval = xcschk(Config);
495  }
496  else if (! strcmp(var,"pfc.decisionlib"))
497  {
498  retval = xdlib(Config);
499  }
500  else if (! strcmp(var,"pfc.purgelib"))
501  {
502  retval = xplib(Config);
503  }
504  else if (! strcmp(var,"pfc.trace"))
505  {
506  retval = xtrace(Config);
507  }
508  else if (! strcmp(var,"pfc.allow_xrdpfc_command"))
509  {
510  m_configuration.m_allow_xrdpfc_command = true;
511  }
512  else if (! strncmp(var,"pfc.", 4))
513  {
514  retval = ConfigParameters(std::string(var+4), Config, tmpc);
515  }
516 
517  if ( ! retval)
518  {
519  TRACE(Error, "Config() error in parsing");
520  aOK = false;
521  }
522  }
523 
524  Config.Close();
525 
526  // Load OSS plugin.
527  auto orig_runmode = myEnv->Get("oss.runmode");
528  myEnv->Put("oss.runmode", "pfc");
529  if (m_configuration.is_cschk_cache())
530  {
531  char csi_conf[128];
532  if (snprintf(csi_conf, 128, "space=%s nofill", m_configuration.m_meta_space.c_str()) < 128)
533  {
534  ofsCfg->Push(XrdOfsConfigPI::theOssLib, "libXrdOssCsi.so", csi_conf);
535  } else {
536  TRACE(Error, "Config() buffer too small for libXrdOssCsi params.");
537  return false;
538  }
539  }
540  if (ofsCfg->Load(XrdOfsConfigPI::theOssLib, myEnv))
541  {
542  ofsCfg->Plugin(m_oss);
543  }
544  else
545  {
546  TRACE(Error, "Config() Unable to create an OSS object");
547  return false;
548  }
549  if (orig_runmode) myEnv->Put("oss.runmode", orig_runmode);
550  else myEnv->Put("oss.runmode", "");
551 
552  // Test if OSS is operational, determine optional features.
553  aOK &= test_oss_basics_and_features();
554 
555  // sets default value for disk usage
556  XrdOssVSInfo sP;
557  {
558  if (m_configuration.m_meta_space != m_configuration.m_data_space &&
559  m_oss->StatVS(&sP, m_configuration.m_meta_space.c_str(), 1) < 0)
560  {
561  m_log.Emsg("ConfigParameters()", "error obtaining stat info for meta space ", m_configuration.m_meta_space.c_str());
562  return false;
563  }
564  if (m_configuration.m_meta_space != m_configuration.m_data_space && sP.Total < 10ll << 20)
565  {
566  m_log.Emsg("ConfigParameters()", "available data space is less than 10 MB (can be due to a mistake in oss.localroot directive) for space ",
567  m_configuration.m_meta_space.c_str());
568  return false;
569  }
570  if (m_oss->StatVS(&sP, m_configuration.m_data_space.c_str(), 1) < 0)
571  {
572  m_log.Emsg("ConfigParameters()", "error obtaining stat info for data space ", m_configuration.m_data_space.c_str());
573  return false;
574  }
575  if (sP.Total < 10ll << 20)
576  {
577  m_log.Emsg("ConfigParameters()", "available data space is less than 10 MB (can be due to a mistake in oss.localroot directive) for space ",
578  m_configuration.m_data_space.c_str());
579  return false;
580  }
581 
582  m_configuration.m_diskTotalSpace = sP.Total;
583 
584  if (cfg2bytes(tmpc.m_diskUsageLWM, m_configuration.m_diskUsageLWM, sP.Total, "lowWatermark") &&
585  cfg2bytes(tmpc.m_diskUsageHWM, m_configuration.m_diskUsageHWM, sP.Total, "highWatermark"))
586  {
587  if (m_configuration.m_diskUsageLWM >= m_configuration.m_diskUsageHWM) {
588  m_log.Emsg("ConfigParameters()", "pfc.diskusage should have lowWatermark < highWatermark.");
589  aOK = false;
590  }
591  }
592  else aOK = false;
593 
594  if ( ! tmpc.m_fileUsageMax.empty())
595  {
596  if (cfg2bytes(tmpc.m_fileUsageBaseline, m_configuration.m_fileUsageBaseline, sP.Total, "files baseline") &&
597  cfg2bytes(tmpc.m_fileUsageNominal, m_configuration.m_fileUsageNominal, sP.Total, "files nominal") &&
598  cfg2bytes(tmpc.m_fileUsageMax, m_configuration.m_fileUsageMax, sP.Total, "files max"))
599  {
600  if (m_configuration.m_fileUsageBaseline >= m_configuration.m_fileUsageNominal ||
601  m_configuration.m_fileUsageBaseline >= m_configuration.m_fileUsageMax ||
602  m_configuration.m_fileUsageNominal >= m_configuration.m_fileUsageMax)
603  {
604  m_log.Emsg("ConfigParameters()", "pfc.diskusage files should have baseline < nominal < max.");
605  aOK = false;
606  }
607 
608 
609  if (aOK && m_configuration.m_fileUsageMax >= m_configuration.m_diskUsageLWM)
610  {
611  m_log.Emsg("ConfigParameters()", "pfc.diskusage files values must be below lowWatermark");
612  aOK = false;
613  }
614  }
615  else aOK = false;
616  }
617  }
618 
619  // sets flush frequency
620  if ( ! tmpc.m_flushRaw.empty())
621  {
622  if (::isalpha(*(tmpc.m_flushRaw.rbegin())))
623  {
624  if (XrdOuca2x::a2sz(m_log, "Error getting number of bytes written before flush", tmpc.m_flushRaw.c_str(),
625  &m_configuration.m_flushCnt,
626  100 * m_configuration.m_bufferSize , 100000 * m_configuration.m_bufferSize))
627  {
628  return false;
629  }
630  m_configuration.m_flushCnt /= m_configuration.m_bufferSize;
631  }
632  else
633  {
634  if (XrdOuca2x::a2ll(m_log, "Error getting number of blocks written before flush", tmpc.m_flushRaw.c_str(),
635  &m_configuration.m_flushCnt, 100, 100000))
636  {
637  return false;
638  }
639  }
640  }
641 
642  // set the write mode
643  if ( ! tmpc.m_writemodeRaw.empty())
644  {
645  if (tmpc.m_writemodeRaw == "writethrough")
646  {
647  m_configuration.m_write_through = true;
648  }
649  else if (tmpc.m_writemodeRaw != "off")
650  {
651  m_log.Emsg("ConfigParameters()", "Unknown value for pfc.writemode (valid values are `writethrough` or `off`): %s",
652  tmpc.m_writemodeRaw.c_str());
653  return false;
654  }
655  }
656 
657  // get number of available RAM blocks after process configuration
658  if (m_configuration.m_RamAbsAvailable == 0)
659  {
660  m_configuration.m_RamAbsAvailable = m_isClient ? 256ll * 1024 * 1024 : 1024ll * 1024 * 1024;
661  char buff[1024];
662  snprintf(buff, sizeof(buff), "RAM usage pfc.ram is not specified. Default value %s is used.", m_isClient ? "256m" : "1g");
663  m_log.Say("Config info: ", buff);
664  }
665  // Setup number of standard-size blocks not released back to the system to 5% of total RAM.
666  m_configuration.m_RamKeepStdBlocks = (m_configuration.m_RamAbsAvailable / m_configuration.m_bufferSize + 1) * 5 / 100;
667 
668  // Set tracing to debug if this is set in environment
669  char* cenv = getenv("XRDDEBUG");
670  if (cenv && ! strcmp(cenv,"1") && m_trace->What < 4) m_trace->What = 4;
671 
672  if (aOK)
673  {
674 // 000 001 010
675  const char *csc[] = {"off", "cache nonet", "nocache net notls",
676 // 011
677  "cache net notls",
678 // 100 101 110
679  "off", "cache nonet", "nocache net tls",
680 // 111
681  "cache net tls"};
682  char uvk[32];
683  if (m_configuration.m_cs_UVKeep < 0)
684  strcpy(uvk, "lru");
685  else
686  sprintf(uvk, "%lld", (long long) m_configuration.m_cs_UVKeep);
687  float ram_gb = (m_configuration.m_RamAbsAvailable) / float(1024*1024*1024);
688 
689  char urlcgi_blks[64] = "ignore", urlcgi_npref[32] = "ignore";
690  if (CFG.m_cgi_blocksize_allowed)
691  snprintf(urlcgi_blks, sizeof(urlcgi_blks), "%lldk %lldk",
692  CFG.m_cgi_min_bufferSize >> 10, CFG.m_cgi_max_bufferSize >> 10);
693  if (CFG.m_cgi_prefetch_allowed)
694  snprintf(urlcgi_npref, sizeof(urlcgi_npref), "%d %d",
696 
697  char buff[8192];
698  int loff = 0;
699  loff = snprintf(buff, sizeof(buff), "Config effective %s pfc configuration:\n"
700  " pfc.cschk %s uvkeep %s\n"
701  " pfc.blocksize %lldk\n"
702  " pfc.prefetch %d\n"
703  " pfc.urlcgi blocksize %s prefetch %s\n"
704  " pfc.ram %.fg\n"
705  " pfc.writequeue %d %d\n"
706  " # Total available disk: %lld\n"
707  " pfc.diskusage %lld %lld files %lld %lld %lld purgeinterval %d purgecoldfiles %d\n"
708  " pfc.spaces %s %s\n"
709  " pfc.trace %d\n"
710  " pfc.flush %lld\n"
711  " pfc.acchistorysize %d\n"
712  " pfc.onlyIfCachedMinBytes %lld\n"
713  " pfc.onlyIfCachedMinFrac %.2f\n",
714  config_filename,
715  csc[int(m_configuration.m_cs_Chk)], uvk,
716  m_configuration.m_bufferSize >> 10,
717  m_configuration.m_prefetch_max_blocks,
718  urlcgi_blks, urlcgi_npref,
719  ram_gb,
720  m_configuration.m_wqueue_blocks, m_configuration.m_wqueue_threads,
721  sP.Total,
722  m_configuration.m_diskUsageLWM, m_configuration.m_diskUsageHWM,
723  m_configuration.m_fileUsageBaseline, m_configuration.m_fileUsageNominal, m_configuration.m_fileUsageMax,
724  m_configuration.m_purgeInterval, m_configuration.m_purgeColdFilesAge,
725  m_configuration.m_data_space.c_str(),
726  m_configuration.m_meta_space.c_str(),
727  m_trace->What,
728  m_configuration.m_flushCnt,
729  m_configuration.m_accHistorySize,
730  m_configuration.m_onlyIfCachedMinSize,
731  m_configuration.m_onlyIfCachedMinFrac);
732 
733  if (m_configuration.is_dir_stat_reporting_on())
734  {
735  loff += snprintf(buff + loff, sizeof(buff) - loff,
736  " pfc.dirstats interval %d maxdepth %d (internal: size_of_dirlist %d, size_of_globlist %d)\n",
737  m_configuration.m_dirStatsInterval, m_configuration.m_dirStatsStoreDepth,
738  (int) m_configuration.m_dirStatsDirs.size(), (int) m_configuration.m_dirStatsDirGlobs.size());
739  loff += snprintf(buff + loff, sizeof(buff) - loff, " dirlist:\n");
740  for (std::set<std::string>::iterator i = m_configuration.m_dirStatsDirs.begin(); i != m_configuration.m_dirStatsDirs.end(); ++i)
741  loff += snprintf(buff + loff, sizeof(buff) - loff, " %s\n", i->c_str());
742  loff += snprintf(buff + loff, sizeof(buff) - loff, " globlist:\n");
743  for (std::set<std::string>::iterator i = m_configuration.m_dirStatsDirGlobs.begin(); i != m_configuration.m_dirStatsDirGlobs.end(); ++i)
744  loff += snprintf(buff + loff, sizeof(buff) - loff, " %s/*\n", i->c_str());
745  }
746 
747  if (m_configuration.m_hdfsmode)
748  {
749  loff += snprintf(buff + loff, sizeof(buff) - loff, " pfc.hdfsmode hdfsbsize %lld\n", m_configuration.m_hdfsbsize);
750  }
751  loff += snprintf(buff + loff, sizeof(buff) - loff, " pfc.writemode %s\n", m_configuration.m_write_through ? "writethrough" : "off");
752 
753  if (m_configuration.m_username.empty())
754  {
755  char unameBuff[256];
756  XrdOucUtils::UserName(getuid(), unameBuff, sizeof(unameBuff));
757  m_configuration.m_username = unameBuff;
758  }
759  else
760  {
761  loff += snprintf(buff + loff, sizeof(buff) - loff, " pfc.user %s\n", m_configuration.m_username.c_str());
762  }
763 
764  m_log.Say(buff);
765 
766  m_env->Put("XRDPFC.SEGSIZE", std::to_string(m_configuration.m_bufferSize).c_str());
767  }
768 
769  // Derived settings
770  m_prefetch_enabled = CFG.m_prefetch_max_blocks > 0 || CFG.m_cgi_max_prefetch_max_blocks > 0;
772 
773  m_gstream = (XrdXrootdGStream*) m_env->GetPtr("pfc.gStream*");
774 
775  m_log.Say(" pfc g-stream has", m_gstream ? "" : " NOT", " been configured via xrootd.monitor directive\n");
776 
777  // Create the ResourceMonitor and get it ready for starting the main thread function.
778  if (aOK)
779  {
780  m_res_mon = new ResourceMonitor(*m_oss);
781  m_res_mon->init_before_main();
782  }
783 
784  m_log.Say("=====> Proxy file cache configuration parsing ", aOK ? "completed" : "failed");
785 
786  if (ofsCfg) delete ofsCfg;
787 
788  // XXXX-CKSUM Testing. To be removed after OssPgi is also merged and valildated.
789  // Building of xrdpfc_print fails when this is enabled.
790 #ifdef XRDPFC_CKSUM_TEST
791  {
792  int xxx = m_configuration.m_cs_Chk;
793 
794  for (m_configuration.m_cs_Chk = CSChk_None; m_configuration.m_cs_Chk <= CSChk_Both; ++m_configuration.m_cs_Chk)
795  {
796  Info::TestCksumStuff();
797  }
798 
799  m_configuration.m_cs_Chk = xxx;
800  }
801 #endif
802 
803  return aOK;
804 }
805 
806 //------------------------------------------------------------------------------
807 
808 bool Cache::ConfigParameters(std::string part, XrdOucStream& config, TmpConfiguration &tmpc)
809 {
810  struct ConfWordGetter
811  {
812  XrdOucStream &m_config;
813  char *m_last_word;
814 
815  ConfWordGetter(XrdOucStream& c) : m_config(c), m_last_word((char*)1) {}
816 
817  const char* GetWord() { if (HasLast()) m_last_word = m_config.GetWord(); return HasLast() ? m_last_word : ""; }
818  bool HasLast() { return (m_last_word != 0); }
819  };
820 
821  ConfWordGetter cwg(config);
822 
823  Configuration &CFG = m_configuration;
824 
825  if ( part == "user" )
826  {
827  m_configuration.m_username = cwg.GetWord();
828  if ( ! cwg.HasLast())
829  {
830  m_log.Emsg("Config", "Error: pfc.user requires a parameter.");
831  return false;
832  }
833  }
834  else if ( part == "diskusage" )
835  {
836  tmpc.m_diskUsageLWM = cwg.GetWord();
837  tmpc.m_diskUsageHWM = cwg.GetWord();
838 
839  if (tmpc.m_diskUsageHWM.empty())
840  {
841  m_log.Emsg("Config", "Error: pfc.diskusage parameter requires at least two arguments.");
842  return false;
843  }
844 
845  const char *p = 0;
846  while ((p = cwg.GetWord()) && cwg.HasLast())
847  {
848  if (strcmp(p, "files") == 0)
849  {
850  tmpc.m_fileUsageBaseline = cwg.GetWord();
851  tmpc.m_fileUsageNominal = cwg.GetWord();
852  tmpc.m_fileUsageMax = cwg.GetWord();
853 
854  if ( ! cwg.HasLast())
855  {
856  m_log.Emsg("Config", "Error: pfc.diskusage files directive requires three arguments.");
857  return false;
858  }
859  }
860  else if (strcmp(p, "sleep") == 0 || strcmp(p, "purgeinterval") == 0)
861  {
862  if (strcmp(p, "sleep") == 0) m_log.Emsg("Config", "warning sleep directive is deprecated in pfc.diskusage. Please use purgeinterval instead.");
863 
864  if (XrdOuca2x::a2tm(m_log, "Error getting purgeinterval", cwg.GetWord(), &m_configuration.m_purgeInterval, 60, 3600))
865  {
866  return false;
867  }
868  }
869  else if (strcmp(p, "purgecoldfiles") == 0)
870  {
871  if (XrdOuca2x::a2tm(m_log, "Error getting purgecoldfiles age", cwg.GetWord(), &m_configuration.m_purgeColdFilesAge, 3600, 3600*24*360))
872  {
873  return false;
874  }
875  if (XrdOuca2x::a2i(m_log, "Error getting purgecoldfiles period", cwg.GetWord(), &m_configuration.m_purgeAgeBasedPeriod, 1, 1000))
876  {
877  return false;
878  }
879  }
880  else
881  {
882  m_log.Emsg("Config", "Error: diskusage stanza contains unknown directive", p);
883  }
884  }
885  }
886  else if ( part == "acchistorysize" )
887  {
888  if ( XrdOuca2x::a2i(m_log, "Error getting access-history-size", cwg.GetWord(), &m_configuration.m_accHistorySize, 20, 200))
889  {
890  return false;
891  }
892  }
893  else if ( part == "dirstats" )
894  {
895  const char *p = 0;
896  while ((p = cwg.GetWord()) && cwg.HasLast())
897  {
898  if (strcmp(p, "interval") == 0)
899  {
900  int validIntervals[] = {60, 120, 300, 600, 900, 1200, 1800, 3600};
901  int size = sizeof(validIntervals) / sizeof(int);
902 
903  if (XrdOuca2x::a2tm(m_log, "Error getting dirstsat interval", cwg.GetWord(),
904  &m_configuration.m_dirStatsInterval, validIntervals[0], validIntervals[size - 1]))
905  {
906  return false;
907  }
908  bool match = false, round_down = false;
909  for (int i = 0; i < size; i++) {
910  if (validIntervals[i] == m_configuration.m_dirStatsInterval) {
911  match = true;
912  break;
913  }
914  if (i > 0 && m_configuration.m_dirStatsInterval < validIntervals[i]) {
915  m_configuration.m_dirStatsInterval = validIntervals[i - 1];
916  round_down = true;
917  break;
918  }
919  }
920  if ( ! match && ! round_down) {
921  m_log.Emsg("Config", "Error: dirstat interval parsing failed.");
922  return false;
923  }
924  if (round_down) {
925  m_log.Emsg("Config", "Info: dirstat interval was rounded down to the nearest valid value.");
926  }
927 
928  }
929  else if (strcmp(p, "maxdepth") == 0)
930  {
931  if (XrdOuca2x::a2i(m_log, "Error getting maxdepth value", cwg.GetWord(),
932  &m_configuration.m_dirStatsStoreDepth, 0, 16))
933  {
934  return false;
935  }
936  }
937  else if (strcmp(p, "dir") == 0)
938  {
939  p = cwg.GetWord();
940  if (p && p[0] == '/')
941  {
942  // XXX -- should we just store them as sets of PathTokenizer objects, not strings?
943 
944  char d[1024]; d[0] = 0;
945  int depth = 0;
946  { // Compress multiple slashes and "measure" depth
947  const char *pp = p;
948  char *pd = d;
949  *(pd++) = *(pp++);
950  while (*pp != 0)
951  {
952  if (*(pd - 1) == '/')
953  {
954  if (*pp == '/')
955  {
956  ++pp; continue;
957  }
958  ++depth;
959  }
960  *(pd++) = *(pp++);
961  }
962  *(pd--) = 0;
963  // remove trailing but but not leading /
964  if (*pd == '/' && pd != d) *pd = 0;
965  }
966  int ld = strlen(d);
967  if (ld >= 2 && d[ld-1] == '*' && d[ld-2] == '/')
968  {
969  d[ld-2] = 0;
970  ld -= 2;
971  m_configuration.m_dirStatsDirGlobs.insert(d);
972  printf("Glob %s -> %s -- depth = %d\n", p, d, depth);
973  }
974  else
975  {
976  m_configuration.m_dirStatsDirs.insert(d);
977  printf("Dir %s -> %s -- depth = %d\n", p, d, depth);
978  }
979 
980  m_configuration.m_dirStatsStoreDepth = std::max(m_configuration.m_dirStatsStoreDepth, depth);
981  }
982  else
983  {
984  m_log.Emsg("Config", "Error: dirstats dir parameter requires a directory argument starting with a '/'.");
985  return false;
986  }
987  }
988  else
989  {
990  m_log.Emsg("Config", "Error: dirstats stanza contains unknown directive '", p, "'");
991  return false;
992  }
993  }
994  }
995  else if ( part == "blocksize" )
996  {
997  if ( ! blocksize_str2value("Config", cwg.GetWord(), CFG.m_bufferSize,
999  return false;
1000  }
1001  else if ( part == "prefetch" || part == "nramprefetch" )
1002  {
1003  if (part == "nramprefetch")
1004  {
1005  m_log.Emsg("Config", "pfc.nramprefetch is deprecated, please use pfc.prefetch instead. Replacing the directive internally.");
1006  }
1007 
1008  if ( ! prefetch_str2value("Config", cwg.GetWord(), CFG.m_prefetch_max_blocks,
1009  0, CFG.s_max_prefetch_max_blocks))
1010  return false;
1011  }
1012  else if ( part == "urlcgi" )
1013  {
1014  // pfc.urlcgi [blocksize {ignore | min max}] [prefetch {ignore | min max}]
1015  const char *p = 0;
1016  while ((p = cwg.GetWord()) && cwg.HasLast())
1017  {
1018  if (strcmp(p, "blocksize") == 0)
1019  {
1020  std::string bmin = cwg.GetWord();
1021  if (bmin == "ignore")
1022  continue;
1023  std::string bmax = cwg.GetWord();
1024  if ( ! cwg.HasLast()) {
1025  m_log.Emsg("Config", "Error: pfc.urlcgi blocksize parameter requires two arguments.");
1026  return false;
1027  }
1028  if ( ! blocksize_str2value("Config::urlcgi", bmin.c_str(), CFG.m_cgi_min_bufferSize,
1030  return false;
1031  if ( ! blocksize_str2value("Config::urlcgi", bmax.c_str(), CFG.m_cgi_max_bufferSize,
1033  return false;
1035  m_log.Emsg("Config", "Error: pfc.urlcgi blocksize second argument must be larger or equal to the first one.");
1036  return false;
1037  }
1038  CFG.m_cgi_blocksize_allowed = true;
1039  }
1040  else if (strcmp(p, "prefetch") == 0)
1041  {
1042  std::string bmin = cwg.GetWord();
1043  if (bmin == "ignore")
1044  continue;
1045  std::string bmax = cwg.GetWord();
1046  if ( ! cwg.HasLast()) {
1047  m_log.Emsg("Config", "Error: pfc.urlcgi blocksize parameter requires two arguments.");
1048  return false;
1049  }
1050  if ( ! prefetch_str2value("Config::urlcgi", bmin.c_str(), CFG.m_cgi_min_prefetch_max_blocks,
1051  0, CFG.s_max_prefetch_max_blocks))
1052  return false;
1053  if ( ! prefetch_str2value("Config::urlcgi", bmax.c_str(), CFG.m_cgi_max_prefetch_max_blocks,
1054  0, CFG.s_max_prefetch_max_blocks))
1055  return false;
1057  m_log.Emsg("Config", "Error: pfc.urlcgi prefetch second argument must be larger or equal to the first one.");
1058  return false;
1059  }
1060  CFG.m_cgi_prefetch_allowed = true;
1061  }
1062  else
1063  {
1064  m_log.Emsg("Config", "Error: urlcgi stanza contains unknown directive '", p, "'");
1065  return false;
1066  }
1067  } // while get next pfc.urlcgi word
1068  }
1069  else if ( part == "nramread" )
1070  {
1071  m_log.Emsg("Config", "pfc.nramread is deprecated, please use pfc.ram instead. Ignoring this directive.");
1072  cwg.GetWord(); // Ignoring argument.
1073  }
1074  else if ( part == "ram" )
1075  {
1076  long long minRAM = m_isClient ? 256 * 1024 * 1024 : 1024 * 1024 * 1024;
1077  long long maxRAM = 256 * minRAM;
1078  if ( XrdOuca2x::a2sz(m_log, "get RAM available", cwg.GetWord(), &m_configuration.m_RamAbsAvailable, minRAM, maxRAM))
1079  {
1080  return false;
1081  }
1082  }
1083  else if ( part == "writequeue")
1084  {
1085  if (XrdOuca2x::a2i(m_log, "Error getting pfc.writequeue num-blocks", cwg.GetWord(), &m_configuration.m_wqueue_blocks, 1, 1024))
1086  {
1087  return false;
1088  }
1089  if (XrdOuca2x::a2i(m_log, "Error getting pfc.writequeue num-threads", cwg.GetWord(), &m_configuration.m_wqueue_threads, 1, 64))
1090  {
1091  return false;
1092  }
1093  }
1094  else if ( part == "spaces" )
1095  {
1096  m_configuration.m_data_space = cwg.GetWord();
1097  m_configuration.m_meta_space = cwg.GetWord();
1098  if ( ! cwg.HasLast())
1099  {
1100  m_log.Emsg("Config", "spacenames requires two parameters: <data-space> <metadata-space>.");
1101  return false;
1102  }
1103  }
1104  else if ( part == "hdfsmode" )
1105  {
1106  m_log.Emsg("Config", "pfc.hdfsmode is currently unsupported.");
1107  return false;
1108 
1109  m_configuration.m_hdfsmode = true;
1110 
1111  const char* params = cwg.GetWord();
1112  if (params)
1113  {
1114  if (! strncmp("hdfsbsize", params, 9))
1115  {
1116  long long minBlSize = 32 * 1024;
1117  long long maxBlSize = 128 * 1024 * 1024;
1118  if ( XrdOuca2x::a2sz(m_log, "Error getting file fragment size", cwg.GetWord(), &m_configuration.m_hdfsbsize, minBlSize, maxBlSize))
1119  {
1120  return false;
1121  }
1122  }
1123  else
1124  {
1125  m_log.Emsg("Config", "Error setting the fragment size parameter name");
1126  return false;
1127  }
1128  }
1129  }
1130  else if ( part == "writemode" )
1131  {
1132  tmpc.m_writemodeRaw = cwg.GetWord();
1133  if ( ! cwg.HasLast())
1134  {
1135  m_log.Emsg("Config", "Error: pfc.writemode requires a parameter.");
1136  return false;
1137  }
1138  }
1139  else if ( part == "flush" )
1140  {
1141  tmpc.m_flushRaw = cwg.GetWord();
1142  if ( ! cwg.HasLast())
1143  {
1144  m_log.Emsg("Config", "Error: pfc.flush requires a parameter.");
1145  return false;
1146  }
1147  }
1148  else if ( part == "onlyifcached" )
1149  {
1150  const char *p = 0;
1151  while ((p = cwg.GetWord()) && cwg.HasLast())
1152  {
1153  if (strcmp(p, "minsize") == 0)
1154  {
1155  std::string minBytes = cwg.GetWord();
1156  long long minBytesTop = 1024 * 1024 * 1024;
1157  if (::isalpha(*(minBytes.rbegin())))
1158  {
1159  if (XrdOuca2x::a2sz(m_log, "Error in parsing minsize value for onlyifcached parameter", minBytes.c_str(), &m_configuration.m_onlyIfCachedMinSize, 0, minBytesTop))
1160  {
1161  return false;
1162  }
1163  }
1164  else
1165  {
1166  if (XrdOuca2x::a2ll(m_log, "Error in parsing numeric minsize value for onlyifcached parameter", minBytes.c_str(),&m_configuration.m_onlyIfCachedMinSize, 0, minBytesTop))
1167  {
1168  return false;
1169  }
1170  }
1171  }
1172  if (strcmp(p, "minfrac") == 0)
1173  {
1174  std::string minFrac = cwg.GetWord();
1175  char *eP;
1176  errno = 0;
1177  double frac = strtod(minFrac.c_str(), &eP);
1178  if (errno || eP == minFrac.c_str())
1179  {
1180  m_log.Emsg("Config", "Error setting fraction for only-if-cached directive");
1181  return false;
1182  }
1183  m_configuration.m_onlyIfCachedMinFrac = frac;
1184  }
1185  else
1186  {
1187  m_log.Emsg("Config", "Error: onlyifcached stanza contains unknown directive", p);
1188  }
1189  }
1190  }
1191  else
1192  {
1193  m_log.Emsg("ConfigParameters() unmatched pfc parameter", part.c_str());
1194  return false;
1195  }
1196 
1197  return true;
1198 }
#define XrdOssOK
Definition: XrdOss.hh:50
#define XRDOSS_mkpath
Definition: XrdOss.hh:466
XrdSysXAttr * XrdSysXAttrActive
Definition: XrdSysFAttr.cc:61
XrdVERSIONINFO(XrdOucGetCache, XrdPfc)
XrdOucCache * XrdOucGetCache(XrdSysLogger *logger, const char *config_filename, const char *parameters, XrdOucEnv *env)
Definition: XrdPfc.cc:76
#define open
Definition: XrdPosix.hh:76
int isNo(int dflt, const char *Msg1, const char *Msg2, const char *Msg3)
if(Avsz)
@ Error
#define TRACE(act, x)
Definition: XrdTrace.hh:63
bool Parse(TheLib what)
bool Plugin(XrdAccAuthorize *&piP)
Get Authorization plugin.
static XrdOfsConfigPI * New(const char *cfn, XrdOucStream *cfgP, XrdSysError *errP, XrdVersionInfo *verP=0, XrdSfsFileSystem *sfsP=0)
bool Load(int what, XrdOucEnv *envP=0)
bool Push(TheLib what, const char *plugP, const char *parmP=0)
@ theOssLib
Oss plugin.
virtual int Close(long long *retsz=0)=0
virtual int getFD()
Definition: XrdOss.hh:426
virtual int Open(const char *path, int Oflag, mode_t Mode, XrdOucEnv &env)
Definition: XrdOss.hh:200
virtual ssize_t Write(const void *buffer, off_t offset, size_t size)
Definition: XrdOss.hh:345
long long Total
Definition: XrdOssVS.hh:90
virtual int Create(const char *tid, const char *path, mode_t mode, XrdOucEnv &env, int opts=0)=0
virtual int Lfn2Pfn(const char *Path, char *buff, int blen)
Definition: XrdOss.hh:873
virtual int StatVS(XrdOssVSInfo *vsP, const char *sname=0, int updt=0)
Definition: XrdOss.cc:117
virtual XrdOssDF * newFile(const char *tident)=0
virtual int Unlink(const char *path, int Opts=0, XrdOucEnv *envP=0)=0
static int Export(const char *Var, const char *Val)
Definition: XrdOucEnv.cc:188
void * GetPtr(const char *varname)
Definition: XrdOucEnv.cc:281
char * Get(const char *varname)
Definition: XrdOucEnv.hh:69
void Put(const char *varname, const char *value)
Definition: XrdOucEnv.hh:85
void * Resolve(const char *symbl, int mcnt=1)
void Unload(bool dodel=false)
char * GetWord(int lowcase=0)
static int UserName(uid_t uID, char *uName, int uNsz)
static int a2i(XrdSysError &, const char *emsg, const char *item, int *val, int minv=-1, int maxv=-1)
Definition: XrdOuca2x.cc:45
static int a2sz(XrdSysError &, const char *emsg, const char *item, long long *val, long long minv=-1, long long maxv=-1)
Definition: XrdOuca2x.cc:257
static int a2ll(XrdSysError &, const char *emsg, const char *item, long long *val, long long minv=-1, long long maxv=-1)
Definition: XrdOuca2x.cc:70
static int a2tm(XrdSysError &, const char *emsg, const char *item, int *val, int minv=-1, int maxv=-1)
Definition: XrdOuca2x.cc:288
bool blocksize_str2value(const char *from, const char *str, long long &val, long long min, long long max) const
bool Config(const char *config_filename, const char *parameters, XrdOucEnv *env)
Parse configuration file.
bool prefetch_str2value(const char *from, const char *str, int &val, int min, int max) const
Base class for selecting which files should be cached.
virtual bool ConfigDecision(const char *params)
Status of cached file. Can be read from and written into a binary file.
Definition: XrdPfcInfo.hh:41
static size_t s_maxNumAccess
Definition: XrdPfcInfo.hh:311
Base class for reguesting directory space to obtain.
virtual bool ConfigPurgePin(const char *params)
int Emsg(const char *esfx, int ecode, const char *text1, const char *text2=0)
Definition: XrdSysError.cc:95
void Say(const char *text1, const char *text2=0, const char *txt3=0, const char *text4=0, const char *text5=0, const char *txt6=0)
Definition: XrdSysError.cc:141
virtual int Get(const char *Aname, void *Aval, int Avsz, const char *Path, int fd=-1)=0
virtual int Set(const char *Aname, const void *Aval, int Avsz, const char *Path, int fd=-1, int isNew=0)=0
XrdCmsConfig Config
Definition: XrdPfc.hh:41
const char * trace_what_strings[]
@ CSChk_Both
Definition: XrdPfcTypes.hh:27
@ CSChk_Net
Definition: XrdPfcTypes.hh:27
@ CSChk_TLS
Definition: XrdPfcTypes.hh:28
@ CSChk_Cache
Definition: XrdPfcTypes.hh:27
@ CSChk_None
Definition: XrdPfcTypes.hh:27
Contains parameters configurable from the xrootd config file.
Definition: XrdPfc.hh:64
long long m_hdfsbsize
used with m_hdfsmode, default 128MB
Definition: XrdPfc.hh:122
long long m_RamAbsAvailable
available from configuration
Definition: XrdPfc.hh:109
long long m_flushCnt
nuber of unsynced blcoks on disk before flush is called
Definition: XrdPfc.hh:123
long long m_cgi_max_bufferSize
max buffer size allowed in pfc.blocksize
Definition: XrdPfc.hh:116
int m_accHistorySize
max number of entries in access history part of cinfo file
Definition: XrdPfc.hh:101
int m_cgi_min_prefetch_max_blocks
min prefetch block count allowed in pfc.prefetch
Definition: XrdPfc.hh:117
bool m_cgi_prefetch_allowed
allow cgi setting of prefetch
Definition: XrdPfc.hh:120
int m_wqueue_threads
number of threads writing blocks to disk
Definition: XrdPfc.hh:112
bool m_write_through
flag indicating write-through mode is enabled
Definition: XrdPfc.hh:84
long long m_diskTotalSpace
total disk space on configured partition or oss space
Definition: XrdPfc.hh:92
long long m_fileUsageMax
cache purge - files usage maximum
Definition: XrdPfc.hh:97
long long m_fileUsageBaseline
cache purge - files usage baseline
Definition: XrdPfc.hh:95
int m_dirStatsStoreDepth
maximum depth for statistics write out
Definition: XrdPfc.hh:106
bool m_allow_xrdpfc_command
flag for enabling access to /xrdpfc-command/ functionality.
Definition: XrdPfc.hh:86
long long m_diskUsageHWM
cache purge - disk usage high water mark
Definition: XrdPfc.hh:94
bool is_cschk_cache() const
Definition: XrdPfc.hh:75
std::set< std::string > m_dirStatsDirGlobs
directory globs for which stat reporting was requested
Definition: XrdPfc.hh:104
static constexpr long long s_min_bufferSize
Definition: XrdPfc.hh:132
static constexpr long long s_max_bufferSize
Definition: XrdPfc.hh:133
int m_prefetch_max_blocks
default maximum number of blocks to prefetch per file
Definition: XrdPfc.hh:113
bool m_cs_ChkTLS
Allow TLS.
Definition: XrdPfc.hh:127
long long m_fileUsageNominal
cache purge - files usage nominal
Definition: XrdPfc.hh:96
int m_cs_Chk
Checksum check.
Definition: XrdPfc.hh:126
int m_purgeAgeBasedPeriod
peform cold file / uvkeep purge every this many purge cycles
Definition: XrdPfc.hh:100
bool m_hdfsmode
flag for enabling block-level operation
Definition: XrdPfc.hh:85
int m_purgeColdFilesAge
purge files older than this age
Definition: XrdPfc.hh:99
std::string m_data_space
oss space for data files
Definition: XrdPfc.hh:89
std::set< std::string > m_dirStatsDirs
directories for which stat reporting was requested
Definition: XrdPfc.hh:103
long long m_diskUsageLWM
cache purge - disk usage low water mark
Definition: XrdPfc.hh:93
int m_RamKeepStdBlocks
number of standard-sized blocks kept after release
Definition: XrdPfc.hh:110
long long m_bufferSize
cache block size, default 128 kB
Definition: XrdPfc.hh:108
long long m_cgi_min_bufferSize
min buffer size allowed in pfc.blocksize
Definition: XrdPfc.hh:115
int m_dirStatsInterval
time between resource monitor statistics dump in seconds
Definition: XrdPfc.hh:105
std::string m_meta_space
oss space for metadata files (cinfo)
Definition: XrdPfc.hh:90
int m_wqueue_blocks
maximum number of blocks written per write-queue loop
Definition: XrdPfc.hh:111
int m_cgi_max_prefetch_max_blocks
max prefetch block count allowed in pfc.prefetch
Definition: XrdPfc.hh:118
std::string m_username
username passed to oss plugin
Definition: XrdPfc.hh:88
static constexpr int s_max_prefetch_max_blocks
Definition: XrdPfc.hh:135
bool m_cgi_blocksize_allowed
allow cgi setting of blocksize
Definition: XrdPfc.hh:119
bool is_cschk_net() const
Definition: XrdPfc.hh:76
double m_onlyIfCachedMinFrac
minimum fraction of downloaded file, used by only-if-cached CGI option
Definition: XrdPfc.hh:130
time_t m_cs_UVKeep
unverified checksum cache keep
Definition: XrdPfc.hh:125
int m_purgeInterval
sleep interval between cache purges
Definition: XrdPfc.hh:98
long long m_onlyIfCachedMinSize
minumum size of downloaded file, used by only-if-cached CGI option
Definition: XrdPfc.hh:129
bool is_dir_stat_reporting_on() const
Definition: XrdPfc.hh:70
std::string m_writemodeRaw
Definition: XrdPfc.hh:148
std::string m_diskUsageLWM
Definition: XrdPfc.hh:142
std::string m_diskUsageHWM
Definition: XrdPfc.hh:143
std::string m_fileUsageBaseline
Definition: XrdPfc.hh:144
std::string m_fileUsageNominal
Definition: XrdPfc.hh:145
std::string m_flushRaw
Definition: XrdPfc.hh:147
std::string m_fileUsageMax
Definition: XrdPfc.hh:146