nfs-ganesha 1.4
|
00001 /* 00002 * vim:expandtab:shiftwidth=8:tabstop=8: 00003 * 00004 * Copyright CEA/DAM/DIF (2008) 00005 * contributeur : Philippe DENIEL philippe.deniel@cea.fr 00006 * Thomas LEIBOVICI thomas.leibovici@cea.fr 00007 * 00008 * 00009 * This program is free software; you can redistribute it and/or 00010 * modify it under the terms of the GNU Lesser General Public 00011 * License as published by the Free Software Foundation; either 00012 * version 3 of the License, or (at your option) any later version. 00013 * 00014 * This program is distributed in the hope that it will be useful, 00015 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00016 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00017 * Lesser General Public License for more details. 00018 * 00019 * You should have received a copy of the GNU Lesser General Public 00020 * License along with this library; if not, write to the Free Software 00021 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA 00022 * 00023 * --------------------------------------- 00024 */ 00025 00038 #ifdef HAVE_CONFIG_H 00039 #include "config.h" 00040 #endif 00041 00042 #ifdef _SOLARIS 00043 #include "solaris_port.h" 00044 #endif /* _SOLARIS */ 00045 00046 #include "LRU_List.h" 00047 #include "log.h" 00048 #include "HashData.h" 00049 #include "HashTable.h" 00050 #include "fsal.h" 00051 #include "cache_inode.h" 00052 #include "cache_content.h" 00053 #include "config_parsing.h" 00054 00055 #include <unistd.h> 00056 #include <sys/types.h> 00057 #include <sys/param.h> 00058 #include <time.h> 00059 #include <pthread.h> 00060 #include <string.h> 00061 00062 char fcc_log_path[MAXPATHLEN]; 00063 int fcc_debug_level = -1; 00064 00065 /* 00066 * 00067 * cache_content_read_conf_client_parameter: read the configuration for a client to File Content layer. 00068 * 00069 * Reads the configuration for a client to File Content layer (typically a worker thread). 00070 * 00071 * @param in_config [IN] configuration file handle 00072 * @param pparam [OUT] read parameters 00073 * 00074 * @return CACHE_CONTENT_SUCCESS if ok, CACHE_CONTENT_INVALID_ARGUMENT otherwise. 00075 * 00076 */ 00077 cache_content_status_t cache_content_read_conf_client_parameter(config_file_t in_config, 00078 cache_content_client_parameter_t * pparam) 00079 { 00080 int var_max; 00081 int var_index; 00082 int err; 00083 char *key_name; 00084 char *key_value; 00085 config_item_t block; 00086 00087 int DebugLevel = -1; 00088 char *LogFile = NULL; 00089 00090 /* Is the config tree initialized ? */ 00091 if(in_config == NULL || pparam == NULL) 00092 return CACHE_CONTENT_INVALID_ARGUMENT; 00093 00094 /* Get the config BLOCK */ 00095 if((block = config_FindItemByName(in_config, CONF_LABEL_CACHE_CONTENT_CLIENT)) == NULL) 00096 { 00097 /* fprintf(stderr, "Cannot read item \"%s\" from configuration file\n", CONF_LABEL_CACHE_CONTENT_CLIENT ) ; */ 00098 return CACHE_CONTENT_NOT_FOUND; 00099 } 00100 else if(config_ItemType(block) != CONFIG_ITEM_BLOCK) 00101 { 00102 /* Expected to be a block */ 00103 return CACHE_CONTENT_INVALID_ARGUMENT; 00104 } 00105 00106 var_max = config_GetNbItems(block); 00107 00108 for(var_index = 0; var_index < var_max; var_index++) 00109 { 00110 config_item_t item; 00111 00112 item = config_GetItemByIndex(block, var_index); 00113 00114 /* Get key's name */ 00115 if((err = config_GetKeyValue(item, &key_name, &key_value)) != 0) 00116 { 00117 fprintf(stderr, 00118 "Error reading key[%d] from section \"%s\" of configuration file.\n", 00119 var_index, CONF_LABEL_CACHE_CONTENT_CLIENT); 00120 return CACHE_CONTENT_INVALID_ARGUMENT; 00121 } 00122 00123 else if(!strcasecmp(key_name, "LRU_Nb_Call_Gc_invalid")) 00124 { 00125 //pparam->lru_param.nb_call_gc_invalid = atoi( key_value ) ; 00126 } 00127 else if(!strcasecmp(key_name, "Cache_Directory")) 00128 { 00129 strcpy(pparam->cache_dir, key_value); 00130 } 00131 else if(!strcasecmp(key_name, "Refresh_FSAL_Force")) 00132 { 00133 pparam->flush_force_fsal = atoi(key_value); 00134 } 00135 else if(!strcasecmp(key_name, "DebugLevel")) 00136 { 00137 DebugLevel = ReturnLevelAscii(key_value); 00138 00139 if(DebugLevel == -1) 00140 { 00141 LogCrit(COMPONENT_CACHE_CONTENT, 00142 "cache_content_read_conf: ERROR: Invalid debug level name: \"%s\".", 00143 key_value); 00144 return CACHE_CONTENT_INVALID_ARGUMENT; 00145 } 00146 } 00147 else if(!strcasecmp(key_name, "LogFile")) 00148 { 00149 LogFile = key_value; 00150 } 00151 else if(!strcasecmp(key_name, "Max_Fd")) 00152 { 00153 pparam->max_fd = atoi(key_value); 00154 } 00155 else if(!strcasecmp(key_name, "Use_OpenClose_cache")) 00156 { 00157 pparam->use_fd_cache = StrToBoolean(key_value); 00158 } 00159 else 00160 { 00161 fprintf(stderr, 00162 "Unknown or unsettable key: %s (item %s)\n", 00163 key_name, CONF_LABEL_CACHE_CONTENT_CLIENT); 00164 return CACHE_CONTENT_INVALID_ARGUMENT; 00165 } 00166 } 00167 00168 fcc_debug_level = DebugLevel; 00169 if(LogFile) { 00170 LogEvent(COMPONENT_INIT, "Setting log file of emergency cache flush thread to %s", 00171 LogFile); 00172 strncpy(fcc_log_path, LogFile, MAXPATHLEN); 00173 } 00174 else { 00175 LogDebug(COMPONENT_INIT, "No log file set for emergency cache flush thread in configuration. Setting to default.") ; 00176 strncpy(fcc_log_path, "/dev/null", MAXPATHLEN); 00177 } 00178 00179 /* init logging */ 00180 if(LogFile) 00181 SetComponentLogFile(COMPONENT_CACHE_CONTENT, LogFile); 00182 00183 if(DebugLevel > -1) 00184 SetComponentLogLevel(COMPONENT_CACHE_CONTENT, DebugLevel); 00185 00186 return CACHE_CONTENT_SUCCESS; 00187 } /* cache_content_read_conf_client_parameter */ 00188 00201 void cache_content_print_conf_client_parameter(FILE * output, 00202 cache_content_client_parameter_t param) 00203 { 00204 /* @todo BUGAZOMEU virer ces deux lignes */ 00205 //fprintf( output, "FileContent Client: LRU_Prealloc_PoolSize = %d\n", param.lru_param.nb_entry_prealloc ) ; 00206 //fprintf( output, "FileContent Client: LRU_Nb_Call_Gc_invalid = %d\n", param.lru_param.nb_call_gc_invalid ) ; 00207 fprintf(output, "FileContent Client: Entry_Prealloc_PoolSize = %d\n", 00208 param.nb_prealloc_entry); 00209 fprintf(output, "FileContent Client: Cache Directory = %s\n", param.cache_dir); 00210 } /* cache_content_print_conf_client_parameter */ 00211 00224 cache_content_status_t cache_content_read_conf_gc_policy(config_file_t in_config, 00225 cache_content_gc_policy_t * 00226 ppolicy) 00227 { 00228 int var_max; 00229 int var_index; 00230 int err; 00231 char *key_name; 00232 char *key_value; 00233 config_item_t block; 00234 00235 /* Is the config tree initialized ? */ 00236 if(in_config == NULL || ppolicy == NULL) 00237 return CACHE_CONTENT_INVALID_ARGUMENT; 00238 00239 /* Get the config BLOCK */ 00240 if((block = config_FindItemByName(in_config, CONF_LABEL_CACHE_CONTENT_GCPOL)) == NULL) 00241 { 00242 /* fprintf(stderr, "Cannot read item \"%s\" from configuration file\n", CONF_LABEL_CACHE_CONTENT_GCPOL ) ; */ 00243 return CACHE_CONTENT_NOT_FOUND; 00244 } 00245 else if(config_ItemType(block) != CONFIG_ITEM_BLOCK) 00246 { 00247 /* Expected to be a block */ 00248 return CACHE_CONTENT_INVALID_ARGUMENT; 00249 } 00250 00251 var_max = config_GetNbItems(block); 00252 00253 for(var_index = 0; var_index < var_max; var_index++) 00254 { 00255 config_item_t item; 00256 00257 item = config_GetItemByIndex(block, var_index); 00258 00259 /* Get key's name */ 00260 if((err = config_GetKeyValue(item, &key_name, &key_value)) != 0) 00261 { 00262 LogCrit(COMPONENT_CONFIG, 00263 "Error reading key[%d] from section \"%s\" of configuration file.", 00264 var_index, CONF_LABEL_CACHE_CONTENT_GCPOL); 00265 return CACHE_CONTENT_INVALID_ARGUMENT; 00266 } 00267 00268 if(!strcasecmp(key_name, "Lifetime")) 00269 { 00270 ppolicy->lifetime = atoi(key_value); 00271 } 00272 else if(!strcasecmp(key_name, "Runtime_Interval")) 00273 { 00274 ppolicy->run_interval = atoi(key_value); 00275 } 00276 else if(!strcasecmp(key_name, "Nb_Call_Before_GC")) 00277 { 00278 ppolicy->nb_call_before_gc = atoi(key_value); 00279 } 00280 else if(!strcasecmp(key_name, "Df_HighWater")) 00281 { 00282 ppolicy->hwmark_df = atoi(key_value); 00283 } 00284 else if(!strcasecmp(key_name, "Df_LowWater")) 00285 { 00286 ppolicy->lwmark_df = atoi(key_value); 00287 } 00288 else if(!strcasecmp(key_name, "Emergency_Grace_Delay")) 00289 { 00290 ppolicy->emergency_grace_delay = atoi(key_value); 00291 } 00292 else 00293 { 00294 LogCrit(COMPONENT_CONFIG, 00295 "Unknown or unsettable key: %s (item %s)", 00296 key_name, CONF_LABEL_CACHE_CONTENT_GCPOL); 00297 return CACHE_CONTENT_INVALID_ARGUMENT; 00298 } 00299 00300 } 00301 return CACHE_CONTENT_SUCCESS; 00302 } /* cache_content_read_conf_gc_policy */ 00303 00316 void cache_content_print_conf_gc_policy(FILE * output, cache_content_gc_policy_t gcpolicy) 00317 { 00318 fprintf(output, "Garbage Policy: Lifetime = %u\n", 00319 (unsigned int)gcpolicy.lifetime); 00320 fprintf(output, "Garbage Policy: Df_HighWater = %u%%\n", gcpolicy.hwmark_df); 00321 fprintf(output, "Garbage Policy: Df_LowWater = %u%%\n", gcpolicy.lwmark_df); 00322 fprintf(output, "Garbage Policy: Emergency Grace Delay = %u\n", 00323 (unsigned int)gcpolicy.emergency_grace_delay); 00324 fprintf(output, "Garbage Policy: Nb_Call_Before_GC = %u\n", 00325 gcpolicy.nb_call_before_gc); 00326 fprintf(output, "Garbage Policy: Runtime_Interval = %u\n", gcpolicy.run_interval); 00327 } /* cache_content_print_gc_pol */