#include <Remote_Tokens.h>
Inheritance diagram for ACE_Remote_Token_Proxy:
Public Member Functions | |
ACE_Remote_Token_Proxy (void) | |
Null construction. | |
virtual | ~ACE_Remote_Token_Proxy (void) |
Death. | |
int | open (const ACE_TCHAR *name, int ignore_deadlock=0, int debug=0) |
int | initiate_connection (void) |
virtual int | acquire (int notify=0, void(*sleep_hook)(void *)=0, ACE_Synch_Options &options=ACE_Synch_Options::synch) |
virtual int | tryacquire (void(*sleep_hook)(void *)=0) |
virtual int | renew (int requeue_position=0, ACE_Synch_Options &options=ACE_Synch_Options::synch) |
virtual int | release (ACE_Synch_Options &options=ACE_Synch_Options::synch) |
virtual int | remove (ACE_Synch_Options &options=ACE_Synch_Options::synch) |
virtual void | token_acquired (ACE_TPQ_Entry *) |
Override the default to do nothing. | |
virtual const ACE_TCHAR * | owner_id (void) |
The client id of the current token holder. | |
void | dump (void) const |
Dump the state of the class. | |
Static Public Member Functions | |
void | set_server_address (const ACE_INET_Addr &server_address) |
Protected Member Functions | |
int | request_reply (ACE_Token_Request &request, ACE_Synch_Options &options) |
Perform the request and wait for the reply. | |
Protected Attributes | |
int | ignore_shadow_deadlock_ |
If shadows report deadlock, go remote anyway. |
The Remote_Token_Proxy class implements the mechanisms for distributed token operations. It is similar to the ACE_Token_Proxy. = BUGS Distributed sleep_hooks have not been implemented. is not implemented.
Definition at line 48 of file Remote_Tokens.h.
|
Null construction.
Definition at line 102 of file Remote_Tokens.cpp. References ACE_TRACE.
00103 { 00104 ACE_TRACE ("ACE_Remote_Token_Proxy::ACE_Remote_Token_Proxy"); 00105 } |
|
Death.
Definition at line 107 of file Remote_Tokens.cpp. References ACE_TRACE.
00108 { 00109 ACE_TRACE ("ACE_Remote_Token_Proxy::~ACE_Remote_Token_Proxy"); 00110 } |
|
Acquire the distributed token. If notify is specified and the token is already held, the owner is notified. options contains the timeout value for the acquire call. The timer is kept at the token server. Asynchronous operations are not supported. Returns 0 on success, -1 on failure with == problem. Reimplemented from ACE_Token_Proxy. Definition at line 187 of file Remote_Tokens.cpp. References ACE_DEBUG, ACE_ERROR_RETURN, ACE_LIB_TEXT, ACE_RETURN, ACE_TRACE, ACE_Token_Proxy::acquire(), ACE_Token_Proxy::client_id(), EDEADLK, EWOULDBLOCK, ignore_shadow_deadlock_, LM_DEBUG, LM_ERROR, ACE_Tokens::make_owner(), ACE_Token_Proxy::name(), ACE_Token_Request::notify(), ACE_Token_Proxy::release(), request_reply(), ACE_Token_Proxy::type(), and ACE_Tokens::type().
00190 { 00191 ACE_TRACE ("ACE_Remote_Token_Proxy::acquire"); 00192 00193 // First grab the local shadow mutex. 00194 if (ACE_Token_Proxy::acquire (notify, 00195 sleep_hook, 00196 ACE_Synch_Options::asynch) == -1) 00197 { 00198 // Acquire failed, deal with it... 00199 switch (errno) 00200 { 00201 case EWOULDBLOCK : 00202 // Whoah, we detected wouldblock via the shadow mutex! 00203 if (debug_) 00204 ACE_DEBUG ((LM_DEBUG, ACE_LIB_TEXT ("(%t) shadow: acquire will block, owner is %s\n"), 00205 this->token_->owner_id ())); 00206 // No error, but would block, 00207 break; 00208 00209 case EDEADLK : 00210 if (debug_) 00211 ACE_DEBUG ((LM_DEBUG, ACE_LIB_TEXT ("(%t) shadow: deadlock detected\n"))); 00212 00213 if (ignore_shadow_deadlock_) 00214 break; 00215 else 00216 { 00217 errno = EDEADLK; 00218 ACE_RETURN (-1); 00219 } 00220 00221 default : 00222 ACE_ERROR_RETURN ((LM_ERROR, 00223 ACE_LIB_TEXT ("(%t) %p shadow acquire failed\n"), 00224 ACE_LIB_TEXT ("ACE_Remote_Token_Proxy")), 00225 -1); 00226 } 00227 } 00228 00229 ACE_Token_Request request (token_->type (), 00230 this->type (), 00231 ACE_Token_Request::ACQUIRE, 00232 this->name (), 00233 this->client_id (), 00234 options); 00235 00236 request.notify (notify); 00237 00238 int result = this->request_reply (request, options); 00239 00240 if (result == -1) 00241 { 00242 // Update the local shadow copy. 00243 ACE_DEBUG ((LM_DEBUG, ACE_LIB_TEXT ("error on remote acquire, releasing shadow mutex.\n"))); 00244 ACE_Token_Proxy::release (); 00245 } 00246 else 00247 { 00248 ACE_DEBUG ((LM_DEBUG, ACE_LIB_TEXT ("(%t) acquired %s remotely.\n"), this->name ())); 00249 // Our shadow call may have failed. However, it's still a race 00250 // to the remote server. If we beat the client which holds the 00251 // local token, we need to fix things locally to reflect the 00252 // actual ownership. All that should happen is that our waiter 00253 // is moved to the front of the waiter list. 00254 token_->make_owner (waiter_); 00255 } 00256 00257 return result; 00258 } |
|
Dump the state of the class.
Reimplemented from ACE_Token_Proxy. Reimplemented in ACE_Remote_Mutex, ACE_Remote_RLock, and ACE_Remote_WLock. Definition at line 393 of file Remote_Tokens.cpp. References ACE_BEGIN_DUMP, ACE_DEBUG, ACE_END_DUMP, ACE_LIB_TEXT, ACE_TRACE, ACE_Token_Proxy::dump(), ignore_shadow_deadlock_, and LM_DEBUG. Referenced by ACE_Remote_WLock::dump(), ACE_Remote_RLock::dump(), and ACE_Remote_Mutex::dump().
00394 { 00395 #if defined (ACE_HAS_DUMP) 00396 ACE_TRACE ("ACE_Remote_Token_Proxy::dump"); 00397 ACE_DEBUG ((LM_DEBUG, ACE_BEGIN_DUMP, this)); 00398 ACE_DEBUG ((LM_DEBUG, ACE_LIB_TEXT ("ACE_Tokens::dump:\n") 00399 ACE_LIB_TEXT (" ignore_shadow_deadlock_ = %d\n"), 00400 ignore_shadow_deadlock_)); 00401 ACE_DEBUG ((LM_DEBUG, ACE_LIB_TEXT ("base:\n"))); 00402 ACE_Token_Proxy::dump (); 00403 ACE_DEBUG ((LM_DEBUG, ACE_END_DUMP)); 00404 #endif /* ACE_HAS_DUMP */ 00405 } |
|
Open a connection with the token server. This only need be used when the user wishes to explicitly open a connection to check if the server exists. Connections are stored in the ACE_Token_Connections singleton as thread-specific data. That is, every thread has only one connection that is used for all remote tokens. Definition at line 130 of file Remote_Tokens.cpp. References ACE_ERROR_RETURN, ACE_LIB_TEXT, ACE_TRACE, and LM_ERROR.
00131 { 00132 ACE_TRACE ("ACE_Remote_Token_Proxy::initiate_connection"); 00133 if (token_ == 0) 00134 { 00135 errno = ENOENT; 00136 ACE_ERROR_RETURN ((LM_ERROR, 00137 ACE_LIB_TEXT ("ACE_Remote_Token_Proxy not open.\n")), -1); 00138 } 00139 00140 ACE_SOCK_Stream *peer = ACE_Token_Connections::instance ()->get_connection (); 00141 return peer == 0 ? 0 : 1; 00142 } |
|
Same as Token_Proxy. is the string uniquely identifying the token. can be 1 to disable deadlock notifications. prints debug messages. Reimplemented from ACE_Token_Proxy. Definition at line 113 of file Remote_Tokens.cpp. References ACE_TCHAR, ACE_TRACE, ignore_shadow_deadlock_, and ACE_Token_Proxy::open().
00116 { 00117 ACE_TRACE ("ACE_Remote_Token_Proxy::open"); 00118 ignore_shadow_deadlock_ = ignore_deadlock; 00119 return ACE_Token_Proxy::open (name, 0, debug); 00120 } |
|
The client id of the current token holder.
Reimplemented from ACE_Token_Proxy. Definition at line 384 of file Remote_Tokens.cpp. References ACE_DEBUG, ACE_LIB_TEXT, ACE_TRACE, and LM_DEBUG.
|
|
Release the distributed token. Similar to ACE_Local_Mutex, if the caller is not the owner, it is removed from the waiter list (if applicable.) Returns 0 on success, -1 on failure with == problem. Reimplemented from ACE_Token_Proxy. Definition at line 342 of file Remote_Tokens.cpp. References ACE_DEBUG, ACE_ERROR, ACE_LIB_TEXT, ACE_TRACE, ACE_Token_Proxy::client_id(), LM_DEBUG, LM_ERROR, ACE_Token_Proxy::name(), ACE_Token_Proxy::release(), request_reply(), ACE_Token_Proxy::type(), and ACE_Tokens::type().
00343 { 00344 ACE_TRACE ("ACE_Remote_Token_Proxy::release"); 00345 00346 ACE_Token_Request request (token_->type (), 00347 this->type (), 00348 ACE_Token_Request::RELEASE, 00349 this->name (), 00350 this->client_id (), 00351 options); 00352 00353 int result = this->request_reply (request, options); 00354 if (result == 0) 00355 ACE_DEBUG ((LM_DEBUG, ACE_LIB_TEXT ("(%t) released %s remotely.\n"), this->name ())); 00356 00357 // whether success or failure, we're going to release the shadow. 00358 // If race conditions exist such that we are no longer the owner, 00359 // this release will perform a remove. 00360 if (ACE_Token_Proxy::release () == -1) 00361 ACE_ERROR ((LM_ERROR, ACE_LIB_TEXT ("(%t) shadow: release failed\n"))); 00362 00363 return result; 00364 } |
|
Become interface compliant for ACE_Guard<>. This has no functionality. Reimplemented from ACE_Token_Proxy. Definition at line 367 of file Remote_Tokens.cpp. References ACE_TRACE.
00368 { 00369 ACE_TRACE ("ACE_Remote_Token_Proxy::remove"); 00370 return 0; 00371 } |
|
Renew the token by offering to release it if there are any other waiters, otherwise get the token back immediately. This renew has the same semantics as ACE_Local_Mutex release. It is semantically equivalent to followed by , but it is faster. options contains the timeout value used if renew blocks. As with acquire, the timer is maintained at the token server. If there are waiters and requeue_position == -1, the caller is queued at the rear of the waiter list. Otherwise, requeue_position specifies the number of waiters to "let by" before reacquiring the token (effectively, the position in the waiter list.) Reimplemented from ACE_Token_Proxy. Definition at line 292 of file Remote_Tokens.cpp. References ACE_DEBUG, ACE_ERROR_RETURN, ACE_LIB_TEXT, ACE_TRACE, ACE_Token_Proxy::client_id(), EWOULDBLOCK, LM_DEBUG, LM_ERROR, ACE_Tokens::make_owner(), ACE_Token_Proxy::name(), ACE_Token_Proxy::release(), ACE_Token_Proxy::renew(), request_reply(), ACE_Token_Request::requeue_position(), ACE_Token_Proxy::type(), and ACE_Tokens::type().
00294 { 00295 ACE_TRACE ("ACE_Remote_Token_Proxy::renew"); 00296 00297 if (ACE_Token_Proxy::renew (requeue_position, 00298 ACE_Synch_Options::asynch) == -1) 00299 { 00300 // Check for error. 00301 if (errno != EWOULDBLOCK) 00302 return -1; 00303 else if (debug_) 00304 ACE_DEBUG ((LM_DEBUG, 00305 ACE_LIB_TEXT ("(%t) shadow: renew would block. owner %s.\n"), 00306 this->token_->owner_id ())); 00307 } 00308 00309 ACE_Token_Request request (token_->type (), 00310 this->type (), 00311 ACE_Token_Request::RENEW, 00312 this->name (), 00313 this->client_id (), 00314 options); 00315 00316 request.requeue_position (requeue_position); 00317 00318 int result = this->request_reply (request, options); 00319 00320 if (result == -1) 00321 { 00322 { 00323 // Save/restore errno. 00324 ACE_Errno_Guard error (errno); 00325 ACE_Token_Proxy::release (); 00326 } 00327 ACE_ERROR_RETURN ((LM_ERROR, 00328 ACE_LIB_TEXT ("%p error on remote renew, releasing shadow mutex.\n"), 00329 ACE_LIB_TEXT ("ACE_Remote_Token_Proxy")), -1); 00330 } 00331 else 00332 { 00333 if (debug_) 00334 ACE_DEBUG ((LM_DEBUG, ACE_LIB_TEXT ("(%t) renewed %s remotely.\n"), this->name ())); 00335 // Make sure that the local shadow reflects our new ownership. 00336 token_->make_owner (waiter_); 00337 return result; 00338 } 00339 } |
|
Perform the request and wait for the reply.
Definition at line 147 of file Remote_Tokens.cpp. References ACE_ERROR_RETURN, ACE_LIB_TEXT, ACE_TRACE, ACE_Token_Request::encode(), LM_ERROR, ACE_SOCK_IO::recv(), ACE_SOCK_Stream::send_n(), and ssize_t. Referenced by acquire(), release(), renew(), and tryacquire().
00149 { 00150 ACE_TRACE ("ACE_Remote_Token_Proxy::request_reply"); 00151 void *buffer; 00152 ssize_t length; 00153 00154 if ((length = request.encode (buffer)) == -1) 00155 ACE_ERROR_RETURN ((LM_ERROR, ACE_LIB_TEXT ("%p\n"), ACE_LIB_TEXT ("encode failed")), -1); 00156 00157 ACE_SOCK_Stream *peer = ACE_Token_Connections::instance ()->get_connection (); 00158 00159 if (peer == 0) 00160 ACE_ERROR_RETURN ((LM_ERROR, "(%P|%t) %p\n", "BIG PROBLEMS with get_connection"), -1); 00161 00162 // Transmit request via a blocking send. 00163 00164 if (peer->send_n (buffer, length) != length) 00165 ACE_ERROR_RETURN ((LM_ERROR, ACE_LIB_TEXT ("%p\n"), ACE_LIB_TEXT ("send_n failed")), -1); 00166 else 00167 { 00168 ACE_Token_Reply reply; 00169 00170 // Receive reply via blocking read. 00171 00172 if (peer->recv (&reply, sizeof reply) != sizeof reply) 00173 ACE_ERROR_RETURN ((LM_ERROR, ACE_LIB_TEXT ("%p\n"), ACE_LIB_TEXT ("recv failed")), -1); 00174 00175 if (reply.decode () == -1) 00176 ACE_ERROR_RETURN ((LM_ERROR, ACE_LIB_TEXT ("%p\n"), ACE_LIB_TEXT ("decode failed")), -1); 00177 00178 errno = int (reply.errnum ()); 00179 if (errno != 0) 00180 return -1; 00181 else 00182 return 0; 00183 } 00184 } |
|
Sets the server address for all instances of ACE_Remote_Token_Proxy If this isn't called, the environment variable TOKEN_SERVER is checked for the server address. If that is not specified, all ACE_Remote_** operations will fail. Definition at line 123 of file Remote_Tokens.cpp. References ACE_TRACE.
00124 { 00125 ACE_TRACE ("ACE_Remote_Token_Proxy::set_server_address"); 00126 ACE_Token_Connections::instance ()->set_server_address (server_address); 00127 } |
|
Override the default to do nothing.
Reimplemented from ACE_Token_Proxy. Definition at line 374 of file Remote_Tokens.cpp. References ACE_DEBUG, ACE_LIB_TEXT, ACE_TRACE, LM_DEBUG, and ACE_Token_Proxy::name().
|
|
Try to acquire the distributed token. If the token is already held, the call returns without queueing the caller as a waiter. Returns 0 on success (the token was acquired), and -1 with EWOULDBLOCK if the token was already held. Reimplemented from ACE_Token_Proxy. Definition at line 261 of file Remote_Tokens.cpp. References ACE_DEBUG, ACE_LIB_TEXT, ACE_TRACE, ACE_Token_Proxy::client_id(), LM_DEBUG, ACE_Token_Proxy::name(), request_reply(), ACE_Token_Proxy::tryacquire(), ACE_Token_Proxy::type(), and ACE_Tokens::type().
00262 { 00263 ACE_TRACE ("ACE_Remote_Token_Proxy::tryacquire"); 00264 00265 // If we can detect locally that the tryacquire will fail, there is 00266 // no need to go remote. 00267 if (ACE_Token_Proxy::tryacquire (sleep_hook) == -1) 00268 { 00269 if (debug_) 00270 { 00271 // Save/restore errno. 00272 ACE_Errno_Guard error (errno); 00273 ACE_DEBUG ((LM_DEBUG, 00274 ACE_LIB_TEXT ("shadow try acquire failed\n"))); 00275 } 00276 00277 return -1; 00278 } 00279 00280 ACE_Token_Request request (token_->type (), 00281 this->type (), 00282 ACE_Token_Request::TRY_ACQUIRE, 00283 this->name (), 00284 this->client_id (), 00285 ACE_Synch_Options::synch); 00286 00287 return this->request_reply (request, 00288 ACE_Synch_Options::synch); 00289 } |
|
If shadows report deadlock, go remote anyway.
Definition at line 148 of file Remote_Tokens.h. |