~ubuntu-branches/ubuntu/utopic/gridengine/utopic

« back to all changes in this revision

Viewing changes to source/libs/lck/test_sge_lock_multiple.c

  • Committer: Bazaar Package Importer
  • Author(s): Mark Hymers
  • Date: 2008-06-25 22:36:13 UTC
  • Revision ID: james.westby@ubuntu.com-20080625223613-tvd9xlhuoct9kyhm
Tags: upstream-6.2~beta2
ImportĀ upstreamĀ versionĀ 6.2~beta2

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*___INFO__MARK_BEGIN__*/
 
2
/*************************************************************************
 
3
 * 
 
4
 *  The Contents of this file are made available subject to the terms of
 
5
 *  the Sun Industry Standards Source License Version 1.2
 
6
 * 
 
7
 *  Sun Microsystems Inc., March, 2001
 
8
 * 
 
9
 * 
 
10
 *  Sun Industry Standards Source License Version 1.2
 
11
 *  =================================================
 
12
 *  The contents of this file are subject to the Sun Industry Standards
 
13
 *  Source License Version 1.2 (the "License"); You may not use this file
 
14
 *  except in compliance with the License. You may obtain a copy of the
 
15
 *  License at http://gridengine.sunsource.net/Gridengine_SISSL_license.html
 
16
 * 
 
17
 *  Software provided under this License is provided on an "AS IS" basis,
 
18
 *  WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING,
 
19
 *  WITHOUT LIMITATION, WARRANTIES THAT THE SOFTWARE IS FREE OF DEFECTS,
 
20
 *  MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE, OR NON-INFRINGING.
 
21
 *  See the License for the specific provisions governing your rights and
 
22
 *  obligations concerning the Software.
 
23
 * 
 
24
 *   The Initial Developer of the Original Code is: Sun Microsystems, Inc.
 
25
 * 
 
26
 *   Copyright: 2003 by Sun Microsystems, Inc.
 
27
 * 
 
28
 *   All Rights Reserved.
 
29
 * 
 
30
 ************************************************************************/
 
31
/*___INFO__MARK_END__*/
 
32
 
 
33
#include <sys/time.h>
 
34
#include <unistd.h>
 
35
#include <stdio.h>
 
36
#include <pthread.h>
 
37
#include <stdlib.h>
 
38
#include <string.h>
 
39
 
 
40
#include "lck/test_sge_lock_main.h"
 
41
#include "lck/sge_lock.h"
 
42
#include "lck/sge_mtutil.h"
 
43
#include "uti/sge_time.h"
 
44
 
 
45
#define MAX_THREADS 6
 
46
 
 
47
/*-------------------------*/
 
48
/* part for the mutex test */
 
49
/*-------------------------*/
 
50
 
 
51
static pthread_mutex_t  mutex = PTHREAD_MUTEX_INITIALIZER;
 
52
static pthread_once_t log_once = PTHREAD_ONCE_INIT;
 
53
 
 
54
/*--------------------------------*/
 
55
/* part for the thread local test */
 
56
/*--------------------------------*/
 
57
static pthread_key_t   state_key;  
 
58
 
 
59
typedef struct {
 
60
   int  value;
 
61
   int  value2;
 
62
}  state_t; 
 
63
 
 
64
static void *thread_function(void *anArg);
 
65
 
 
66
static void state_destroy(void* state) 
 
67
{
 
68
   free(state);
 
69
}
 
70
 
 
71
static void state_init(state_t* state) 
 
72
{
 
73
   state->value = 258;
 
74
   state->value2 = 0;
 
75
}
 
76
 
 
77
/*---------------------------*/
 
78
/* sync part between threads */
 
79
/*---------------------------*/
 
80
 
 
81
typedef struct {
 
82
   pthread_mutex_t    mutex;  
 
83
   int                working;
 
84
   double             time;
 
85
   pthread_cond_t     cond_var;
 
86
}sge_control_t;
 
87
 
 
88
static int threads = MAX_THREADS;
 
89
 
 
90
static sge_control_t Control = {PTHREAD_MUTEX_INITIALIZER, MAX_THREADS,0.0, PTHREAD_COND_INITIALIZER};
 
91
 
 
92
static void has_finished(const char* str, double time) 
 
93
{
 
94
   DENTER(TOP_LAYER, "has_finished");
 
95
 
 
96
   sge_mutex_lock("has_finished", SGE_FUNC, __LINE__, &Control.mutex);
 
97
   Control.working--;
 
98
   Control.time += time;
 
99
 
 
100
   if (Control.working == 0) {
 
101
      Control.working = threads;
 
102
      Control.time /= threads;
 
103
      printf("%s : %fs\n", str, Control.time);
 
104
      Control.time = 0.0;
 
105
      pthread_cond_broadcast(&Control.cond_var);
 
106
      
 
107
   }
 
108
   else {
 
109
      struct timespec ts;
 
110
      ts.tv_sec = (long) (sge_get_gmt() + 180);
 
111
      ts.tv_nsec = 0; 
 
112
      pthread_cond_timedwait(&Control.cond_var,
 
113
                             &Control.mutex, &ts);
 
114
   }
 
115
   
 
116
   sge_mutex_unlock("has_finished", SGE_FUNC, __LINE__, &Control.mutex);
 
117
   
 
118
   DEXIT;
 
119
}
 
120
 
 
121
/*---------------------------*/
 
122
/* part of the general setup */
 
123
/*---------------------------*/
 
124
 
 
125
void set_thread_count(int count) 
 
126
{
 
127
   threads = count;
 
128
   Control.working = count;
 
129
}
 
130
 
 
131
int get_thrd_demand(void)
 
132
{
 
133
   int p = MAX_THREADS;  /* min num of threads */
 
134
 
 
135
   pthread_key_create(&state_key, &state_destroy);
 
136
   
 
137
   return (int)p;
 
138
}
 
139
 
 
140
static void log_once_init(void)
 
141
{
 
142
   return;
 
143
 
144
 
 
145
void *(*get_thrd_func(void))(void *anArg)
 
146
{
 
147
   return thread_function;
 
148
}
 
149
 
 
150
void *get_thrd_func_arg(void)
 
151
{
 
152
   return NULL;
 
153
}
 
154
 
 
155
/****** test_sge_lock_multiple/thread_function() *********************************
 
156
*  NAME
 
157
*     thread_function() -- Thread function to execute 
 
158
*
 
159
*  SYNOPSIS
 
160
*     static void* thread_function(void *anArg) 
 
161
*
 
162
*  FUNCTION
 
163
*     Acquire multiple locks and sleep. Release the locks. After each 'sge_lock()'
 
164
*     and 'sge_unlock()' sleep to increase the probability of interlocked execution. 
 
165
*     Note that we deliberately test the boundaries of 'sge_locktype_t'.
 
166
*
 
167
*  INPUTS
 
168
*     void *anArg - thread function arguments 
 
169
*
 
170
*  RESULT
 
171
*     static void* - none
 
172
*
 
173
*  SEE ALSO
 
174
*     test_sge_lock_multiple/get_thrd_func()
 
175
*******************************************************************************/
 
176
static void *thread_function(void *anArg)
 
177
{
 
178
   struct timeval before;
 
179
   struct timeval after;
 
180
   double time_new;
 
181
   int i;
 
182
   int max = 1000000;
 
183
   int test = 257;
 
184
   int result;
 
185
 
 
186
   DENTER(TOP_LAYER, "thread_function");
 
187
 
 
188
   has_finished("start",0.0);
 
189
 
 
190
   gettimeofday(&before, NULL); 
 
191
   for (i = 0; i < max; i++) {
 
192
      result = test +1;
 
193
      test = result +1;
 
194
   }
 
195
   gettimeofday(&after, NULL);
 
196
 
 
197
   time_new = after.tv_usec - before.tv_usec;
 
198
   time_new = after.tv_sec - before.tv_sec + (time_new/1000000);
 
199
 
 
200
   has_finished("variable access", time_new);
 
201
 
 
202
   gettimeofday(&before, NULL); 
 
203
   for (i = 0; i < max; i++) {
 
204
      GET_SPECIFIC(state_t, state, state_init, state_key, "test_sge_lock_multiple");
 
205
      state->value2 = state->value +1;
 
206
      state->value = state->value2 +1;
 
207
   }
 
208
   gettimeofday(&after, NULL);
 
209
 
 
210
   time_new = after.tv_usec - before.tv_usec;
 
211
   time_new = after.tv_sec - before.tv_sec + (time_new/1000000);
 
212
 
 
213
   has_finished("thread local   ", time_new);
 
214
  
 
215
   gettimeofday(&before, NULL); 
 
216
   for (i = 0; i < max; i++) {
 
217
      pthread_once(&log_once, log_once_init);
 
218
      {
 
219
        GET_SPECIFIC(state_t, state, state_init, state_key, "test_sge_lock_multiple");
 
220
         state->value2 = state->value +1;
 
221
         state->value = state->value2 +1;
 
222
      }
 
223
   }
 
224
   gettimeofday(&after, NULL);
 
225
 
 
226
   time_new = after.tv_usec - before.tv_usec;
 
227
   time_new = after.tv_sec - before.tv_sec + (time_new/1000000);
 
228
 
 
229
   has_finished("thread local once ", time_new);
 
230
   
 
231
   gettimeofday(&before, NULL); 
 
232
   for (i = 0; i < max; i++) {
 
233
      sge_mutex_lock("mutex", SGE_FUNC, __LINE__, &mutex);
 
234
      result = test +1;
 
235
      test = result +1;
 
236
      sge_mutex_unlock("mutex", SGE_FUNC, __LINE__, &mutex);
 
237
   }
 
238
   gettimeofday(&after, NULL);
 
239
 
 
240
   time_new = after.tv_usec - before.tv_usec;
 
241
   time_new = after.tv_sec - before.tv_sec + (time_new/1000000);
 
242
 
 
243
   has_finished("mutex          ", time_new);
 
244
 
 
245
   gettimeofday(&before, NULL); 
 
246
   for (i = 0; i < max; i++) {
 
247
      SGE_LOCK(LOCK_GLOBAL, LOCK_READ);
 
248
      result = test +1;
 
249
      test = result +1;
 
250
      SGE_UNLOCK(LOCK_GLOBAL, LOCK_READ);
 
251
   }
 
252
   gettimeofday(&after, NULL);
 
253
 
 
254
   time_new = after.tv_usec - before.tv_usec;
 
255
   time_new = after.tv_sec - before.tv_sec + (time_new/1000000);
 
256
 
 
257
   has_finished("read lock      ", time_new);
 
258
 
 
259
   gettimeofday(&before, NULL); 
 
260
   for (i = 0; i < max; i++) {
 
261
      SGE_LOCK(LOCK_GLOBAL, LOCK_WRITE);
 
262
      result = test +1;
 
263
      test = result +1;
 
264
      SGE_UNLOCK(LOCK_GLOBAL, LOCK_WRITE);
 
265
   }
 
266
   gettimeofday(&after, NULL);
 
267
 
 
268
   time_new = after.tv_usec - before.tv_usec;
 
269
   time_new = after.tv_sec - before.tv_sec + (time_new/1000000);
 
270
 
 
271
   has_finished("write lock     ", time_new);
 
272
 
 
273
 
 
274
   DEXIT;
 
275
   return (void *)NULL;
 
276
} /* thread_function */