Changeset 8397 for branches/cu-security-branch/src/io/bmi/bmi.c
- Timestamp:
- 06/18/10 20:02:50 (3 years ago)
- Location:
- branches/cu-security-branch
- Files:
-
- 3 modified
-
. (modified) (1 prop)
-
src/io/bmi (modified) (1 prop)
-
src/io/bmi/bmi.c (modified) (17 diffs)
Legend:
- Unmodified
- Added
- Removed
-
branches/cu-security-branch
- Property svn:ignore
-
old new 3 3 aclocal.m4 4 4 autom4te.cache 5 config.status6 Makefile7 pvfs2-config.h8 module.mk
-
- Property svn:ignore
-
branches/cu-security-branch/src/io/bmi
- Property svn:ignore deleted
-
branches/cu-security-branch/src/io/bmi/bmi.c
r8330 r8397 50 50 struct qlist_head link; 51 51 BMI_addr_t addr; 52 }; 53 54 /* 55 * BMI trigger to reap all method resources for inactive addresses. 56 */ 57 static QLIST_HEAD(bmi_addr_force_drop_list); 58 static gen_mutex_t bmi_addr_force_drop_list_mutex = GEN_MUTEX_INITIALIZER; 59 struct drop_item 60 { 61 struct qlist_head link; 62 char *method_name; 52 63 }; 53 64 … … 70 81 #ifdef __STATIC_METHOD_BMI_PORTALS__ 71 82 extern struct bmi_method_ops bmi_portals_ops; 83 #endif 84 #ifdef __STATIC_METHOD_BMI_ZOID__ 85 extern struct bmi_method_ops bmi_zoid_ops; 72 86 #endif 73 87 … … 88 102 &bmi_portals_ops, 89 103 #endif 104 #ifdef __STATIC_METHOD_BMI_ZOID__ 105 &bmi_zoid_ops, 106 #endif 90 107 NULL 91 108 }; … … 110 127 111 128 static struct bmi_method_ops **active_method_table = NULL; 112 static struct { 129 130 struct method_usage_t { 113 131 int iters_polled; /* how many iterations since this method was polled */ 114 132 int iters_active; /* how many iterations since this method had action */ 115 133 int plan; 116 } *method_usage = NULL; 134 int flags; 135 }; 136 137 static struct method_usage_t * expected_method_usage = NULL; 138 static struct method_usage_t * unexpected_method_usage = NULL; 139 117 140 static const int usage_iters_starvation = 100000; 118 141 static const int usage_iters_active = 10000; … … 122 145 int flags); 123 146 static void bmi_addr_drop(ref_st_p tmp_ref); 147 static void bmi_addr_force_drop(ref_st_p ref, ref_list_p ref_list); 124 148 static void bmi_check_forget_list(void); 149 static void bmi_check_addr_force_drop (void); 125 150 126 151 /** Initializes the BMI layer. Must be called before any other BMI … … 518 543 known_method_count = 0; 519 544 520 if (method_usage) 521 free(method_usage); 545 if (expected_method_usage) 546 free(expected_method_usage); 547 548 if (unexpected_method_usage) 549 free(unexpected_method_usage); 522 550 523 551 /* destroy the reference list */ … … 901 929 */ 902 930 static void 903 construct_poll_plan(int nmeth, int *idle_time_ms) 931 construct_poll_plan(struct method_usage_t * method_usage, 932 int nmeth, int *idle_time_ms) 904 933 { 905 934 int i, numplan; … … 910 939 ++method_usage[i].iters_active; 911 940 method_usage[i].plan = 0; 912 if (method_usage[i].iters_active <= usage_iters_active) { 941 if ((method_usage[i].iters_active <= usage_iters_active) && 942 (!(method_usage[i].flags & BMI_METHOD_FLAG_NO_POLLING))){ 913 943 /* recently busy, poll */ 914 944 if (0) gossip_debug(GOSSIP_BMI_DEBUG_CONTROL, … … 967 997 /* figure out if we need to drop any stale addresses */ 968 998 bmi_check_forget_list(); 999 bmi_check_addr_force_drop(); 969 1000 970 1001 gen_mutex_lock(&active_method_count_mutex); … … 977 1008 *outcount = 0; 978 1009 979 construct_poll_plan(tmp_active_method_count, &max_idle_time_ms); 1010 construct_poll_plan(unexpected_method_usage, 1011 tmp_active_method_count, &max_idle_time_ms); 980 1012 981 1013 while (position < incount && i < tmp_active_method_count) 982 1014 { 983 if ( method_usage[i].plan) {1015 if (unexpected_method_usage[i].plan) { 984 1016 ret = active_method_table[i]->testunexpected( 985 1017 (incount - position), &tmp_outcount, … … 993 1025 position += tmp_outcount; 994 1026 (*outcount) += tmp_outcount; 995 method_usage[i].iters_polled = 0;1027 unexpected_method_usage[i].iters_polled = 0; 996 1028 if (ret) 997 method_usage[i].iters_active = 0;1029 unexpected_method_usage[i].iters_active = 0; 998 1030 } 999 1031 i++; … … 1074 1106 } 1075 1107 1076 construct_poll_plan(tmp_active_method_count, &max_idle_time_ms); 1108 construct_poll_plan(expected_method_usage, 1109 tmp_active_method_count, &max_idle_time_ms); 1077 1110 1078 1111 while (position < incount && i < tmp_active_method_count) 1079 1112 { 1080 if ( method_usage[i].plan) {1113 if (expected_method_usage[i].plan) { 1081 1114 ret = active_method_table[i]->testcontext( 1082 1115 incount - position, … … 1096 1129 position += tmp_outcount; 1097 1130 (*outcount) += tmp_outcount; 1098 method_usage[i].iters_polled = 0;1131 expected_method_usage[i].iters_polled = 0; 1099 1132 if (ret) 1100 method_usage[i].iters_active = 0;1133 expected_method_usage[i].iters_active = 0; 1101 1134 } 1102 1135 i++; … … 1202 1235 new_buffer = tmp_ref->interface->memalloc(size, send_recv); 1203 1236 1237 /* initialize buffer, if not NULL. */ 1238 if (new_buffer) 1239 { 1240 memset(new_buffer,0,size); 1241 } 1204 1242 return (new_buffer); 1205 1243 } … … 1981 2019 1982 2020 /* 2021 * Signal BMI to drop inactive connections for this method. 2022 */ 2023 void bmi_method_addr_drop_callback (char* method_name) 2024 { 2025 struct drop_item *item = 2026 (struct drop_item *) malloc(sizeof(struct drop_item)); 2027 2028 /* 2029 * If we can't allocate, just return. 2030 * Maybe this will succeed next time. 2031 */ 2032 if (!item) return; 2033 2034 item->method_name = method_name; 2035 2036 gen_mutex_lock(&bmi_addr_force_drop_list_mutex); 2037 qlist_add(&item->link, &bmi_addr_force_drop_list); 2038 gen_mutex_unlock(&bmi_addr_force_drop_list_mutex); 2039 2040 return; 2041 } 2042 2043 2044 /** 2045 * Try to increase method_usage_t struct to include room for a new method. 2046 */ 2047 static int grow_method_usage (struct method_usage_t ** p, int newflags) 2048 { 2049 struct method_usage_t * x = *p; 2050 *p = malloc((active_method_count + 1) * sizeof(**p)); 2051 if (!*p) { 2052 *p = x; 2053 return 0; 2054 } 2055 if (active_method_count) { 2056 memcpy(*p, x, active_method_count * sizeof(**p)); 2057 free(x); 2058 } 2059 memset(&((*p)[active_method_count]), 0, sizeof(**p)); 2060 (*p)[active_method_count].flags = newflags; 2061 2062 return 1; 2063 } 2064 2065 /* 1983 2066 * Attempt to insert this name into the list of active methods, 1984 2067 * and bring it up. … … 2030 2113 active_method_table[active_method_count] = meth; 2031 2114 2032 x = method_usage; 2033 method_usage = malloc((active_method_count + 1) * sizeof(*method_usage)); 2034 if (!method_usage) { 2035 method_usage = x; 2036 return -ENOMEM; 2037 } 2038 if (active_method_count) { 2039 memcpy(method_usage, x, active_method_count * sizeof(*method_usage)); 2040 free(x); 2041 } 2042 memset(&method_usage[active_method_count], 0, sizeof(*method_usage)); 2115 if (!grow_method_usage (&unexpected_method_usage, meth->flags)) 2116 return -ENOMEM; 2117 2118 /** 2119 * If we run out of memory here, the unexpected_method_usage will be 2120 * larger than strictly required but there is no memory leak. 2121 */ 2122 2123 if (!grow_method_usage (&expected_method_usage, meth->flags)) 2124 return -ENOMEM; 2043 2125 2044 2126 ++active_method_count; … … 2220 2302 } 2221 2303 2304 2305 /* bmi_addr_force_drop 2306 * 2307 * Destroys a complete BMI address, including forcing the method to clean up 2308 * its portion. 2309 * 2310 * NOTE: must be called with ref list mutex held 2311 */ 2312 static void bmi_addr_force_drop(ref_st_p ref, ref_list_p ref_list) 2313 { 2314 gossip_debug(GOSSIP_BMI_DEBUG_CONTROL, 2315 "[BMI CONTROL]: %s: bmi discarding address: %llu\n", 2316 __func__, llu(ref->bmi_addr)); 2317 2318 ref_list_rem(ref_list, ref->bmi_addr); 2319 dealloc_ref_st(ref); 2320 2321 return; 2322 } 2323 2324 /* 2325 * bmi_check_addr_force_drop 2326 * 2327 * Checks to see if any method has requested freeing resources. 2328 */ 2329 static void bmi_check_addr_force_drop (void) 2330 { 2331 struct drop_item *drop_item = NULL; 2332 ref_st_p ref_item = NULL; 2333 2334 gen_mutex_lock(&bmi_addr_force_drop_list_mutex); 2335 while (!qlist_empty(&bmi_addr_force_drop_list)) 2336 { 2337 drop_item = qlist_entry(qlist_pop(&bmi_addr_force_drop_list), 2338 struct drop_item, 2339 link); 2340 gen_mutex_unlock(&bmi_addr_force_drop_list_mutex); 2341 gen_mutex_lock(&ref_mutex); 2342 qlist_for_each_entry(ref_item, cur_ref_list, list_link) 2343 { 2344 if ((ref_item->ref_count == 0) && 2345 (ref_item->interface->method_name == drop_item->method_name)) 2346 { 2347 bmi_addr_force_drop(ref_item, cur_ref_list); 2348 } 2349 } 2350 gen_mutex_unlock(&ref_mutex); 2351 gen_mutex_lock(&bmi_addr_force_drop_list_mutex); 2352 } 2353 gen_mutex_unlock(&bmi_addr_force_drop_list_mutex); 2354 2355 return; 2356 } 2357 2222 2358 /* 2223 2359 * Local variables:
