NCBI C++ ToolKit
ncbi_priv.h
Go to the documentation of this file.

Go to the SVN repository for this file.

1 #ifndef CONNECT___NCBI_PRIV__H
2 #define CONNECT___NCBI_PRIV__H
3 
4 /* $Id: ncbi_priv.h 102329 2024-04-23 19:21:48Z ucko $
5  * ===========================================================================
6  *
7  * PUBLIC DOMAIN NOTICE
8  * National Center for Biotechnology Information
9  *
10  * This software/database is a "United States Government Work" under the
11  * terms of the United States Copyright Act. It was written as part of
12  * the author's official duties as a United States Government employee and
13  * thus cannot be copyrighted. This software/database is freely available
14  * to the public for use. The National Library of Medicine and the U.S.
15  * Government have not placed any restriction on its use or reproduction.
16  *
17  * Although all reasonable efforts have been taken to ensure the accuracy
18  * and reliability of the software and data, the NLM and the U.S.
19  * Government do not and cannot warrant the performance or results that
20  * may be obtained by using this software or data. The NLM and the U.S.
21  * Government disclaim all warranties, express or implied, including
22  * warranties of performance, merchantability or fitness for any particular
23  * purpose.
24  *
25  * Please cite the author in any work or product based on this material.
26  *
27  * ===========================================================================
28  *
29  * Authors: Denis Vakatov, Anton Lavrentiev, Pavel Ivanov
30  *
31  * File Description:
32  * Private aux. code for the "ncbi_*.[ch]"
33  *
34  *********************************
35  * Error handling and logging (including tracing):
36  * C error codes: NCBI_C_DEFINE_ERRCODE_X, NCBI_C_ERRCODE_X
37  * private global: g_CORE_Log
38  * macros: CORE_TRACE[F], CORE_LOG[F][_[EX]X],
39  * CORE_LOG[F]_ERRNO[_[EX]X](), CORE_DATA[F][_[EX]X]
40  * Multi-thread safety (critical section basic MT synchronization):
41  * private globals: g_CORE_MT_Lock[_default]
42  * macros: CORE_LOCK_WRITE, CORE_LOCK_READ, CORE_UNLOCK
43  * Registry:
44  * private global: g_CORE_Registry
45  * macros: CORE_REG_GET, CORE_REG_SET
46  * Setup accounting: ECORE_Set
47  * private global: g_CORE_Set
48  * Random generator seeding support
49  * private global: g_NCBI_ConnectRandomSeed
50  * macro: NCBI_CONNECT_SRAND_ADDEND
51  * App name / NCBI ID / DTab support
52  * private globals: g_CORE_GetAppName
53  * g_CORE_GetReferer
54  * g_CORE_GetRequestID
55  * g_CORE_GetRequestDtab
56  *
57  */
58 
59 /*#define NCBI_MONKEY*/
60 
61 #include "ncbi_assert.h"
62 #include <connect/ncbi_util.h>
63 #ifdef NCBI_MONKEY
64 # ifdef NCBI_OS_MSWIN
65 # include <WinSock2.h>
66 # else
67 # include <sys/socket.h>
68 # endif /*NCBI_OS_MSWIN*/
69 #endif /*NCBI_MONKEY*/
70 
71 
72 #ifdef __cplusplus
73 extern "C" {
74 #endif
75 
76 
77 /******************************************************************************
78  * Error handling and logging
79  *
80  * Several macros brought here from ncbidiag.hpp. The names slightly
81  * changed (added _C) because some sources can include this header and
82  * ncbidiag.hpp simultaneously.
83  */
84 
85 /** Define global error code name with given value (err_code) */
86 #define NCBI_C_DEFINE_ERRCODE_X(name, err_code, max_err_subcode) \
87  enum enum##name { \
88  eErrCodeX_##name = err_code \
89  /* automatic subcode checking is not implemented in C code */ \
90  }
91 
92 /* Here are only error codes used in C sources. For error codes used in
93  * C++ sources (in C++ Toolkit) see include/connect/error_codes.hpp.
94  */
95 NCBI_C_DEFINE_ERRCODE_X(Connect_Conn, 301, 36);
96 NCBI_C_DEFINE_ERRCODE_X(Connect_Socket, 302, 166);
97 NCBI_C_DEFINE_ERRCODE_X(Connect_Util, 303, 15);
98 NCBI_C_DEFINE_ERRCODE_X(Connect_LBSM, 304, 31);
99 NCBI_C_DEFINE_ERRCODE_X(Connect_FTP, 305, 13);
100 NCBI_C_DEFINE_ERRCODE_X(Connect_SMTP, 306, 33);
101 NCBI_C_DEFINE_ERRCODE_X(Connect_HTTP, 307, 26);
102 NCBI_C_DEFINE_ERRCODE_X(Connect_Service, 308, 10);
103 NCBI_C_DEFINE_ERRCODE_X(Connect_HeapMgr, 309, 34);
104 NCBI_C_DEFINE_ERRCODE_X(Connect_TLS, 310, 51);
105 NCBI_C_DEFINE_ERRCODE_X(Connect_Mghbn, 311, 16);
106 NCBI_C_DEFINE_ERRCODE_X(Connect_Crypt, 312, 5);
107 NCBI_C_DEFINE_ERRCODE_X(Connect_LocalIP, 313, 5);
108 NCBI_C_DEFINE_ERRCODE_X(Connect_NamerdLinkerd, 314, 14);
109 
110 
111 /** Make one identifier from 2 parts */
112 #define NCBI_C_CONCAT_IDENTIFIER(prefix, postfix) prefix##postfix
113 
114 /** Return value of error code by its name defined by NCBI_DEFINE_ERRCODE_X
115  *
116  * @sa NCBI_C_DEFINE_ERRCODE_X
117  */
118 #define NCBI_C_ERRCODE_X_NAME(name) \
119  NCBI_C_CONCAT_IDENTIFIER(eErrCodeX_, name)
120 
121 /** Return currently set default error code. Default error code is set by
122  * definition of NCBI_USE_ERRCODE_X with name of error code as its value.
123  *
124  * @sa NCBI_DEFINE_ERRCODE_X
125  */
126 #define NCBI_C_ERRCODE_X \
127  NCBI_C_ERRCODE_X_NAME(NCBI_USE_ERRCODE_X)
128 
129 
131 
132 /* Always use the following macros and functions to access "g_CORE_Log",
133  * do not access/change it directly!
134  */
135 
136 #ifdef _DEBUG
137 # define CORE_TRACE(message) CORE_LOG(eLOG_Trace, message)
138 # define CORE_TRACEF(fmt_args) CORE_LOGF(eLOG_Trace, fmt_args)
139 # define CORE_DEBUG_ARG(arg) arg
140 #else
141 # define CORE_TRACE(message) ((void) 0)
142 # define CORE_TRACEF(fmt_args) ((void) 0)
143 # define CORE_DEBUG_ARG(arg) /*arg*/
144 #endif /*_DEBUG*/
145 
146 #define CORE_LOG_X(subcode, level, message) \
147  DO_CORE_LOG(NCBI_C_ERRCODE_X, subcode, level, \
148  message, 0)
149 
150 #define CORE_LOGF_X(subcode, level, fmt_args) \
151  DO_CORE_LOG(NCBI_C_ERRCODE_X, subcode, level, \
152  g_CORE_Sprintf fmt_args, 1)
153 
154 #define CORE_LOG(level, message) \
155  DO_CORE_LOG(0, 0, level, \
156  message, 0)
157 
158 #define CORE_LOGF(level, fmt_args) \
159  DO_CORE_LOG(0, 0, level, \
160  g_CORE_Sprintf fmt_args, 1)
161 
162 #define CORE_LOG_ERRNO_X(subcode, level, error, message) \
163  DO_CORE_LOG_ERRNO(NCBI_C_ERRCODE_X, subcode, level, error, 0, \
164  message, 0)
165 
166 #define CORE_LOGF_ERRNO_X(subcode, level, error, fmt_args) \
167  DO_CORE_LOG_ERRNO(NCBI_C_ERRCODE_X, subcode, level, error, 0, \
168  g_CORE_Sprintf fmt_args, 1)
169 
170 #define CORE_LOG_ERRNO(level, error, message) \
171  DO_CORE_LOG_ERRNO(0, 0, level, error, 0, \
172  message, 0)
173 
174 #define CORE_LOGF_ERRNO(level, error, fmt_args) \
175  DO_CORE_LOG_ERRNO(0, 0, level, error, 0, \
176  g_CORE_Sprintf fmt_args, 1)
177 
178 #define CORE_LOG_ERRNO_EXX(subcode, level, error, descr, message) \
179  DO_CORE_LOG_ERRNO(NCBI_C_ERRCODE_X, subcode, level, error, descr, \
180  message, 0)
181 
182 #define CORE_LOGF_ERRNO_EXX(subcode, level, error, descr, fmt_args) \
183  DO_CORE_LOG_ERRNO(NCBI_C_ERRCODE_X, subcode, level, error, descr, \
184  g_CORE_Sprintf fmt_args, 1)
185 
186 #define CORE_LOG_ERRNO_EX(level, error, descr, message) \
187  DO_CORE_LOG_ERRNO(0, 0, level, error, descr, \
188  message, 0)
189 
190 #define CORE_LOGF_ERRNO_EX(level, error, descr, fmt_args) \
191  DO_CORE_LOG_ERRNO(0, 0, level, error, descr, \
192  g_CORE_Sprintf fmt_args, 1)
193 
194 #define CORE_DATA_X(subcode, level, data, size, message) \
195  DO_CORE_LOG_DATA(NCBI_C_ERRCODE_X, subcode, level, data, size, \
196  message, 0)
197 
198 #define CORE_DATAF_X(subcode, level, data, size, fmt_args) \
199  DO_CORE_LOG_DATA(NCBI_C_ERRCODE_X, subcode, level, data, size, \
200  g_CORE_Sprintf fmt_args, 1)
201 
202 #define CORE_DATA(level, data, size, message) \
203  DO_CORE_LOG_DATA(0, 0, level, data, size, \
204  message, 0)
205 
206 #define CORE_DATAF(level, data, size, fmt_args) \
207  DO_CORE_LOG_DATA(0, 0, level, data, size, \
208  g_CORE_Sprintf fmt_args, 1)
209 
210 /* helpers follow */
211 #define DO_CORE_LOG_X(_code, _subcode, _level, _message, _dynamic, \
212  _error, _descr, _raw_data, _raw_size) \
213  do { \
214  ELOG_Level _xx_level = (_level); \
215  if (g_CORE_Log || _xx_level == eLOG_Fatal) { \
216  SLOG_Message _mess; \
217  _mess.dynamic = _dynamic; \
218  _mess.message = NcbiMessagePlusError(&_mess.dynamic, \
219  (_message), \
220  (_error), \
221  (_descr)); \
222  _mess.level = _xx_level; \
223  _mess.module = THIS_MODULE; \
224  _mess.func = CORE_CURRENT_FUNCTION; \
225  _mess.file = __FILE__; \
226  _mess.line = __LINE__; \
227  _mess.raw_data = (_raw_data); \
228  _mess.raw_size = (_raw_size); \
229  _mess.err_code = (_code); \
230  _mess.err_subcode = (_subcode); \
231  CORE_LOCK_READ; \
232  LOG_WriteInternal(g_CORE_Log, &_mess); \
233  CORE_UNLOCK; \
234  } \
235  } while (0)
236 
237 #define DO_CORE_LOG(code, subcode, level, \
238  message, dynamic) \
239  DO_CORE_LOG_X(code, subcode, level, message, dynamic, 0, 0, 0, 0)
240 
241 #define DO_CORE_LOG_ERRNO(code, subcode, level, error, descr, \
242  message, dynamic) \
243  DO_CORE_LOG_X(code, subcode, level, message, dynamic, error, descr, 0, 0)
244 
245 #define DO_CORE_LOG_DATA(code, subcode, level, data, size, \
246  message, dynamic) \
247  DO_CORE_LOG_X(code, subcode, level, message, dynamic, 0, 0, data, size)
248 
249 extern NCBI_XCONNECT_EXPORT const char* g_CORE_Sprintf(const char* fmt, ...)
250 #ifdef __GNUC__
251  __attribute__((format(printf,1,2)))
252 #endif /*__GNUC__*/
253 ;
254 
255 
256 /******************************************************************************
257  * Multi-thread safety
258  */
259 
260 extern struct MT_LOCK_tag g_CORE_MT_Lock_default;
261 
263 
264 
265 /* Always use the following macros and functions to access "g_CORE_MT_Lock",
266  * do not access/change it directly!
267  */
268 
269 #define CORE_LOCK_WRITE verify(CORE_CHECK_LOCK != 0 && \
270  MT_LOCK_Do(g_CORE_MT_Lock, eMT_Lock ) != 0)
271 #define CORE_LOCK_READ verify(CORE_CHECK_LOCK != 0 && \
272  MT_LOCK_Do(g_CORE_MT_Lock, eMT_LockRead) != 0)
273 #define CORE_UNLOCK verify(CORE_CHECK_UNLOCK != 0 && \
274  MT_LOCK_Do(g_CORE_MT_Lock, eMT_Unlock ) != 0)
275 
276 #ifdef _DEBUG
279 # define CORE_CHECK_LOCK g_NCBI_CoreCheckLock()
280 # define CORE_CHECK_UNLOCK g_NCBI_CoreCheckUnlock()
281 #else
282 # define CORE_CHECK_LOCK (1/*TRUE*/)
283 # define CORE_CHECK_UNLOCK (1/*TRUE*/)
284 #endif /*_DEBUG*/
285 
286 
287 /******************************************************************************
288  * Registry
289  */
290 
292 
293 /* Always use the following macros to access "g_CORE_Registry",
294  * do not access/change it directly!
295  */
296 
297 #define CORE_REG_GET(section, name, value, value_size, def_value) \
298  g_CORE_RegistryGET(section, name, value, value_size, def_value)
299 
300 #define CORE_REG_SET(section, name, value, storage) \
301  g_CORE_RegistrySET(section, name, value, storage)
302 
303 /* (private, to be used exclusively by the above macro CORE_REG_GET) */
304 extern NCBI_XCONNECT_EXPORT const char* g_CORE_RegistryGET
305 (const char* section,
306  const char* name,
307  char* value,
308  size_t value_size,
309  const char* def_value
310  );
311 
312 /* (private, to be used exclusively by the above macro CORE_REG_SET) */
313 extern NCBI_XCONNECT_EXPORT int/*bool*/ g_CORE_RegistrySET
314 (const char* section,
315  const char* name,
316  const char* value,
317  EREG_Storage storage
318  );
319 
320 
321 /******************************************************************************
322  * Setup accounting
323  */
324 
325 typedef enum {
329  eCORE_SetLOCK = 8
331 typedef unsigned int TCORE_Set;
332 
333 /* Track settings modified from the user-land */
334 extern TCORE_Set g_CORE_Set;
335 
336 
337 /******************************************************************************
338  * Random generator seeding support
339  */
340 
342 extern NCBI_XCONNECT_EXPORT unsigned int g_NCBI_ConnectSrandAddend(void);
343 #define NCBI_CONNECT_SRAND_ADDEND g_NCBI_ConnectSrandAddend()
344 
345 
346 /******************************************************************************
347  * App name support (may return NULL; gets converted to "" at the user level)
348  * The name is assumed to have static storage (not to be free()'d after use).
349  */
350 
351 typedef const char* (*FNcbiGetAppName)(void);
353 
354 
355 /******************************************************************************
356  * Referer support (return NULL or non-empty dynamically malloc()'ed string)
357  */
358 
359 typedef const char* (*FNcbiGetReferer)(void);
361 
362 
363 /******************************************************************************
364  * NCBI request ID support (return "as is" to the user)
365  * Return NULL on error; otherwise, the returned ID is a non-empty string
366  * allocated on heap, and must be free()'d when no longer needed.
367  */
368 
369 typedef char* (*FNcbiGetRequestID)(ENcbiRequestID);
371 
372 
373 /******************************************************************************
374  * DTab-Local support (returned NULL gets converted to "" at the user level)
375  */
376 typedef const char* (*FNcbiGetRequestDtab)(void);
378 
379 
380 /******************************************************************************
381  * Miscellanea
382  */
383 
384 #ifdef __GNUC__
385 # define likely(x) __builtin_expect(!!(x),1)
386 # define unlikely(x) __builtin_expect(!!(x),0)
387 #else
388 # define likely(x) (x)
389 # define unlikely(x) (x)
390 #endif /*__GNUC__*/
391 
392 
393 
394 /******************************************************************************
395  * NCBI Crazy Monkey support
396  */
397 
398 #ifdef NCBI_MONKEY
399 /* UNIX and Windows have different prototypes for send(), recv(), etc., so
400  * some types have to be pre-selected based on current OS
401  */
402 # ifdef NCBI_OS_MSWIN
403 # define MONKEY_RETTYPE int
404 # define MONKEY_SOCKTYPE SOCKET
405 # define MONKEY_DATATYPE char*
406 # define MONKEY_LENTYPE int
407 # define MONKEY_SOCKLENTYPE int
408 # define MONKEY_STDCALL __stdcall /*in Windows, socket functions
409  have prototypes with __stdcall*/
410 # else
411 # define MONKEY_RETTYPE ssize_t
412 # define MONKEY_SOCKTYPE int
413 # define MONKEY_DATATYPE void*
414 # define MONKEY_LENTYPE size_t
415 # define MONKEY_SOCKLENTYPE socklen_t
416 # define MONKEY_STDCALL /*empty*/
417 # endif /*NCBI_OS_MSWIN*/
418 
419 /******************************************************************************
420  * Socket functions via Crazy Monkey
421  */
422 typedef MONKEY_RETTYPE
423  (MONKEY_STDCALL *FMonkeyRecv) (MONKEY_SOCKTYPE socket,
424  MONKEY_DATATYPE buf,
425  MONKEY_LENTYPE size,
426  int flags,
427  void* /* SOCK* */ sock_ptr);
428 typedef MONKEY_RETTYPE
429  (MONKEY_STDCALL *FMonkeySend) (MONKEY_SOCKTYPE socket,
430  const MONKEY_DATATYPE data,
431  MONKEY_LENTYPE size,
432  int flags,
433  void* /* SOCK* */ sock_ptr);
434 typedef int(MONKEY_STDCALL *FMonkeyConnect)(MONKEY_SOCKTYPE socket,
435  const struct sockaddr* name,
436  MONKEY_SOCKLENTYPE namelen);
437 
438 typedef int /*bool*/ (*FMonkeyPoll) (size_t* n,
439  void* /*SSOCK_Poll[]**/polls,
440  EIO_Status* ret_status);
441 typedef void (*FMonkeyClose) (MONKEY_SOCKTYPE socket);
442 typedef void (*FSockHasSocket)(void* /* SOCK */ sock,
443  MONKEY_SOCKTYPE socket);
444 
445 
446 extern NCBI_XCONNECT_EXPORT FMonkeySend g_MONKEY_Send;
447 extern NCBI_XCONNECT_EXPORT FMonkeyRecv g_MONKEY_Recv;
448 extern NCBI_XCONNECT_EXPORT FMonkeyPoll g_MONKEY_Poll;
449 extern NCBI_XCONNECT_EXPORT FMonkeyConnect g_MONKEY_Connect;
450 extern NCBI_XCONNECT_EXPORT FMonkeyClose g_MONKEY_Close;
451 extern NCBI_XCONNECT_EXPORT FSockHasSocket g_MONKEY_SockHasSocket;
452 #endif /*NCBI_MONKEY*/
453 
454 
455 #ifdef __cplusplus
456 } /* extern "C" */
457 #endif
458 
459 #endif /* CONNECT___NCBI_PRIV__H */
static uch flags
char data[12]
Definition: iconv.c:80
EREG_Storage
Transient/Persistent storage.
Definition: ncbi_core.h:528
EIO_Status
I/O status.
Definition: ncbi_core.h:132
ENcbiRequestID
NCBI request ID enumerator.
Definition: ncbi_util.h:432
#define NCBI_XCONNECT_EXPORT
unsigned int
A callback function used to compare two keys in a database.
Definition: types.hpp:1210
char * buf
yy_size_t n
const struct ncbi::grid::netcache::search::fields::SIZE size
const GenericPointer< typename T::ValueType > T2 value
Definition: pointer.h:1227
int g_CORE_RegistrySET(const char *section, const char *name, const char *value, EREG_Storage storage)
Definition: ncbi_priv.c:153
const char *(* FNcbiGetRequestDtab)(void)
Definition: ncbi_priv.h:376
unsigned int g_NCBI_ConnectSrandAddend(void)
Definition: ncbi_priv.c:67
ECORE_Set
Definition: ncbi_priv.h:325
@ eCORE_SetLOCK
Definition: ncbi_priv.h:329
@ eCORE_SetLOG
Definition: ncbi_priv.h:328
@ eCORE_SetSSL
Definition: ncbi_priv.h:326
@ eCORE_SetREG
Definition: ncbi_priv.h:327
unsigned int g_NCBI_ConnectRandomSeed
Definition: ncbi_priv.c:51
int g_NCBI_CoreCheckUnlock(void)
Definition: ncbi_priv.c:92
LOG g_CORE_Log
Definition: ncbi_priv.c:49
const char * g_CORE_Sprintf(const char *fmt,...)
Definition: ncbi_priv.c:107
FNcbiGetRequestDtab g_CORE_GetRequestDtab
Definition: ncbi_priv.c:55
TCORE_Set g_CORE_Set
Definition: ncbi_priv.c:47
REG g_CORE_Registry
Definition: ncbi_priv.c:50
const char *(* FNcbiGetReferer)(void)
Definition: ncbi_priv.h:359
#define NCBI_C_DEFINE_ERRCODE_X(name, err_code, max_err_subcode)
Define global error code name with given value (err_code)
Definition: ncbi_priv.h:86
FNcbiGetRequestID g_CORE_GetRequestID
Definition: ncbi_priv.c:54
FNcbiGetAppName g_CORE_GetAppName
Definition: ncbi_priv.c:52
const char *(* FNcbiGetAppName)(void)
Definition: ncbi_priv.h:351
const char * g_CORE_RegistryGET(const char *section, const char *name, char *value, size_t value_size, const char *def_value)
Definition: ncbi_priv.c:137
MT_LOCK g_CORE_MT_Lock
Definition: ncbi_priv.c:48
char *(* FNcbiGetRequestID)(ENcbiRequestID)
Definition: ncbi_priv.h:369
unsigned int TCORE_Set
Definition: ncbi_priv.h:331
FNcbiGetReferer g_CORE_GetReferer
Definition: ncbi_priv.c:53
int g_NCBI_CoreCheckLock(void)
Definition: ncbi_priv.c:85
struct MT_LOCK_tag g_CORE_MT_Lock_default
Definition: ncbi_core.c:185
static Format format
Definition: njn_ioutil.cpp:53
Modified on Tue May 21 11:00:52 2024 by modify_doxy.py rev. 669887