00001 /* 00002 * rk.h 00003 * 00004 * Copyright (c) 2003 The University of Utah and the Flux Group. 00005 * All rights reserved. 00006 * 00007 * This file is licensed under the terms of the GNU Public License. 00008 * See the file "license.terms" for restrictions on redistribution 00009 * of this file, and for a DISCLAIMER OF ALL WARRANTIES. 00010 */ 00011 00012 /** 00013 * @file rk.h 00014 * 00015 * This file contains a replica of the TimeSys resource control APIs. The goal 00016 * is to provide a close enough approximation that the same code can be used in 00017 * the simulated and real worlds. The only visible difference between the two 00018 * is the definition of RK_STUB, so any simulation specific code should be 00019 * enclosed in an "#if defined(RK_STUB)". 00020 * 00021 * @sa rk_stub.h 00022 */ 00023 00024 #ifndef _rk_h 00025 #define _rk_h 00026 00027 #include <sys/types.h> 00028 #if TIME_WITH_SYS_TIME 00029 # include <sys/time.h> 00030 # include <time.h> 00031 #else 00032 # if HAVE_SYS_TIME_H 00033 # include <sys/time.h> 00034 # else 00035 # include <time.h> 00036 # endif 00037 #endif 00038 00039 #ifdef __cplusplus 00040 extern "C" { 00041 #endif 00042 00043 /** 00044 * Inform the includer that this is the stub version. 00045 */ 00046 #define RK_STUB 1 00047 00048 /** 00049 * Maximum length for resource kernel names in general. 00050 */ 00051 #define RK_NAME_LEN 32 00052 00053 /** 00054 * Maximum length for resource set names. 00055 */ 00056 #define RSET_NAME_LEN RK_NAME_LEN 00057 00058 /** 00059 * Minimum period of periodic process 00060 */ 00061 #define RT_MIN_PERIOD (struct timespec){0, 20000} /* 20uS */ 00062 00063 /** 00064 * Enumeration that can be used to specify which CPU a resource set can be 00065 * bound to. 00066 */ 00067 typedef enum { 00068 RK_ANY_CPU = -1, /**< Use any CPU available on the system. */ 00069 } rk_processor_t; 00070 00071 /** 00072 * The resource reservation modes. 00073 */ 00074 typedef enum { 00075 RSV_HARD = 0x1, /**< Hard reservation */ 00076 RSV_FIRM = 0x2, /**< Firm reservation */ 00077 RSV_SOFT = 0x4, /**< Soft reservation */ 00078 } rk_reserve_mode_t; 00079 00080 /** 00081 * The resource reservation parameters. 00082 * 00083 * XXX Currently, all three fields @e must contain the same RSV value. 00084 */ 00085 typedef struct rk_reserve_param { 00086 rk_reserve_mode_t sch_mode; /**< Scheduling mode */ 00087 rk_reserve_mode_t enf_mode; /**< Enforcement mode */ 00088 rk_reserve_mode_t rep_mode; /**< Replenishment mode */ 00089 } *rk_reserve_param_t; 00090 00091 /** 00092 * The CPU reservation parameters. 00093 */ 00094 typedef struct cpu_reserve_attr { 00095 struct timespec compute_time; 00096 struct timespec period; 00097 struct timespec deadline; 00098 struct timespec blocking_time; 00099 struct timespec start_time; 00100 struct rk_reserve_param reserve_type; 00101 rk_processor_t processor; 00102 } *cpu_reserve_attr_t; 00103 00104 /** 00105 * Opaque reference to a resource set. 00106 */ 00107 typedef struct rk_resource_set *rk_resource_set_t; 00108 00109 /** 00110 * Opaque reference to a resource reserve. 00111 */ 00112 typedef void *rk_reserve_t; 00113 00114 /** 00115 * NULL constant value for a resource set. 00116 */ 00117 #define NULL_RESOURCE_SET ((rk_resource_set_t)0) 00118 00119 /** 00120 * NULL constant value for a reserve. 00121 */ 00122 #define NULL_RESERVE ((rk_reserve_t)0) 00123 00124 /** 00125 * @e Not implemented. 00126 */ 00127 void rk_inherit_mode(int dummy); 00128 00129 /** 00130 * Construct a mock resource set with the given name. The name has special 00131 * meaning in the simulator, it will be used as the base for any files that are 00132 * produced or read by the stub code. For example, a file produced or read by 00133 * the CPU reserve will use file names of the form: <name>_cpu_<file-type>. 00134 * 00135 * @sa rk_cpu_reserve_create 00136 * @sa rk_cpu_reserve_trace_t 00137 * 00138 * @param name The name for the resource set. 00139 * @return A new rk_resource_set_t object or NULL if the creation failed. 00140 */ 00141 rk_resource_set_t rk_resource_set_create(const char *name); 00142 00143 /** 00144 * Destroy a resource set. 00145 * 00146 * @param rs The resource set to destroy. 00147 */ 00148 void rk_resource_set_destroy(rk_resource_set_t rs); 00149 00150 /** 00151 * Set the name of a resource set. This is provided for compatibility and is 00152 * otherwise unwise to use since the name has meaning in the simulation code. 00153 * 00154 * @param rs The resource set to rename. 00155 * @param name The new name. 00156 * @return Zero if the name was valid, an errno value otherwise. 00157 */ 00158 int rk_resource_set_set_name(rk_resource_set_t rs, const char *name); 00159 00160 /** 00161 * Get the name of a resource set. 00162 * 00163 * @param rs The resource set to query. 00164 * @param name_out The character array, of atleast RSET_NAME_LEN length, to 00165 * fill out with the name of the resource set. 00166 * @return Zero if the parameters were valid, an errno value otherwise. 00167 */ 00168 int rk_resource_set_get_name(rk_resource_set_t rs, char *name_out); 00169 00170 /** 00171 * Get the CPU reserve from the given resource set. 00172 * 00173 * @param rs The resource set to query. 00174 * @return A pointer to the CPU reserve or NULL if the resource set did not 00175 * have a CPU reserve attached. 00176 */ 00177 rk_reserve_t rk_resource_set_get_cpu_rsv(rk_resource_set_t rs); 00178 00179 /** 00180 * Attach a process to the resource set so that its callbacks will be used 00181 * when a data period is starting/ending. 00182 * 00183 * @e Note: The simulator only supports one process being attached at a time. 00184 * 00185 * @param rs The resource set that will be attached to the process. 00186 * @param pid The fake process ID to attach to the resource set. 00187 * @return Zero if the process was successfully attached, an errno value 00188 * otherwise. 00189 */ 00190 int rk_resource_set_attach_process(rk_resource_set_t rs, pid_t pid); 00191 00192 /** 00193 * Detach a process to the resource set. 00194 * 00195 * @param rs The attached resource set. 00196 * @param pid The fake process ID to detach from the resource set. 00197 * @return Zero if the process was successfully detached, an errno value 00198 * otherwise. 00199 */ 00200 int rk_resource_set_detach_process(rk_resource_set_t rs, pid_t pid); 00201 00202 /** 00203 * Get the resource set attached to the given process. 00204 * 00205 * @param pid The fake process ID to query. 00206 * @return The resource set that is attached to the process or NULL if none is 00207 * attached. 00208 */ 00209 rk_resource_set_t rk_proc_get_rset(pid_t pid); 00210 00211 /** 00212 * Create a CPU reserve for the given resource set. In order to simulate this 00213 * reserve, a "times" file must be available in the current directory. The 00214 * contents of the file should be a whitespace separated list of floats that 00215 * specify the percentage of CPU time required by the process for a repeating 00216 * sequence of periods. For example, the times file for a resource set named 00217 * "steady_50" that required 50% of the CPU at every period would be named 00218 * "steady_50_cpu_times" and contain only "50.0". Another, more complex 00219 * example, would be a reserve that oscillated between 10% and 50% with 10% 00220 * steps would contain "10.0 20.0 30.0 40.0 50.0 40.0 30.0 20.0 10.0". 00221 * 00222 * The output of CPU simulation is a set of files that can be fed into gnuplot. 00223 * The contents of the file are two columns of numbers, a time value, and a CPU 00224 * percentage or an arbitrary value that marks some event. The current list of 00225 * files is: 00226 * 00227 * @li @e _cpu_period The CPU reserve's period. 00228 * @li @e _cpu_deadline The CPU reserve's deadline. 00229 * @li @e _cpu_complete Marks the completion of a data period. 00230 * @li @e _cpu_drop Marks a data period as being dropped. 00231 * @li @e _cpu_realtime The CPU time required by the process. 00232 * @li @e _cpu_success The actual CPU time received by a process that is making 00233 * its deadlines. 00234 * @li @e _cpu_fail The actual CPU time received by a process that is missing 00235 * its deadlines. 00236 * 00237 * @param rs The resource set that will hold the CPU reserve. 00238 * @param r_out A pointer that can be set to the new CPU reserve. 00239 * @param ra_in The reservation parameters. 00240 * @return Zero if the reserve was created successfully, an errno value 00241 * otherwise. 00242 */ 00243 int rk_cpu_reserve_create(rk_resource_set_t rs, 00244 rk_reserve_t *r_out, 00245 cpu_reserve_attr_t ra_in); 00246 00247 /** 00248 * Delete a CPU reserve held by a resource set. 00249 * 00250 * @param rs A resource set. 00251 */ 00252 void rk_cpu_reserve_delete(rk_resource_set_t rs); 00253 00254 /** 00255 * Get the reservation parameters for a given CPU reserve. 00256 * 00257 * @param cr The CPU reserve to query. 00258 * @param ra_out The cpu_reserve_attr object to fill with the CPU reserve's 00259 * current parameters. 00260 * @return Zero if the query was successful, an errno value otherwise. 00261 */ 00262 int rk_cpu_reserve_get_attr(rk_reserve_t cr, cpu_reserve_attr_t ra_out); 00263 00264 /** 00265 * Change a CPU reserve's scheduling parameters. 00266 * 00267 * @param rs The CPU reserve to change. 00268 * @param ra_in The new scheduling parameters. 00269 * @return Zero if the change was successful, an errno value otherwise. 00270 */ 00271 int rk_cpu_reserve_ctl(rk_resource_set_t rs, cpu_reserve_attr_t ra_in); 00272 00273 #if !defined(HAVE_CLOCKID_T) 00274 /** 00275 * A clockid_t enumeration for those OS's that do not support it. 00276 */ 00277 typedef enum { 00278 CLOCK_REALTIME, 00279 CLOCK_VIRTUAL, 00280 CLOCK_PROF 00281 } clockid_t; 00282 #endif 00283 00284 /** 00285 * Get the simulator's virtual time. 00286 * 00287 * @param clock_id The clock type, only CLOCK_REALTIME is supported. 00288 * @param ts The timespec object to fill out. 00289 * @return Zero if the query was successful, otherwise it returns -1 and sets 00290 * errno appropriately. 00291 */ 00292 int rk_clock_gettime(clockid_t clock_id, struct timespec *ts); 00293 00294 /** 00295 * Set the simulator's virtual time. This function should really only be used 00296 * to set the time to a value _before_ the next event. 00297 * 00298 * @param clock_id The clock type, only CLOCK_REALTIME is supported. 00299 * @param ts The new virtual time value. 00300 * @return Zero if the query was successful, otherwise it returns -1 and sets 00301 * errno appropriately. 00302 */ 00303 int rk_clock_settime(clockid_t clock_id, struct timespec *ts); 00304 00305 /** 00306 * Get the simulator's virtual clock resolution. 00307 * 00308 * @param clock_id The clock type, only CLOCK_REALTIME is supported. 00309 * @param ts The timespec object to fill out. 00310 * @return Zero if the query was successful, otherwise it returns -1 and sets 00311 * errno appropriately. 00312 */ 00313 int rk_clock_getres(clockid_t clock_id, struct timespec *ts); 00314 00315 /** 00316 * @copydoc rk_clock_gettime 00317 */ 00318 #define clock_gettime(clock_id, ts) rk_clock_gettime(clock_id, ts) 00319 00320 /** 00321 * @copydoc rk_clock_settime 00322 */ 00323 #define clock_settime(clock_id, ts) rk_clock_settime(clock_id, ts) 00324 00325 /** 00326 * @copydoc rk_clock_getres 00327 */ 00328 #define clock_getres(clock_id, ts) rk_clock_getres(clock_id, ts) 00329 00330 #ifdef __cplusplus 00331 } 00332 #endif 00333 00334 #endif