BLPAPI C++ 3.25.12
Loading...
Searching...
No Matches
blpapi_correlationid.h
Go to the documentation of this file.
1/* Copyright 2012. Bloomberg Finance L.P.
2 *
3 * Permission is hereby granted, free of charge, to any person obtaining a copy
4 * of this software and associated documentation files (the "Software"), to
5 * deal in the Software without restriction, including without limitation the
6 * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
7 * sell copies of the Software, and to permit persons to whom the Software is
8 * furnished to do so, subject to the following conditions: The above
9 * copyright notice and this permission notice shall be included in all copies
10 * or substantial portions of the Software.
11 *
12 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
13 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
14 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
15 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
16 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
17 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
18 * IN THE SOFTWARE.
19 */
20
28#ifndef INCLUDED_BLPAPI_CORRELATIONID
29#define INCLUDED_BLPAPI_CORRELATIONID
30
61#include <blpapi_call.h>
62#include <blpapi_defs.h>
63#include <blpapi_exception.h>
64#include <blpapi_types.h>
65
66#ifdef __cplusplus
67extern "C" {
68#endif
69
71struct blpapi_ManagedPtr_t_;
72typedef struct blpapi_ManagedPtr_t_ blpapi_ManagedPtr_t;
73
74typedef int (*blpapi_ManagedPtr_ManagerFunction_t)(
75 blpapi_ManagedPtr_t *managedPtr,
76 const blpapi_ManagedPtr_t *srcPtr,
77 int operation);
78
79typedef union {
80 int intValue;
81 void *ptr;
82} blpapi_ManagedPtr_t_data_;
83
84struct blpapi_ManagedPtr_t_ {
85 void *pointer;
86 blpapi_ManagedPtr_t_data_ userData[4];
87 blpapi_ManagedPtr_ManagerFunction_t manager;
88};
89
90typedef struct blpapi_CorrelationId_t_ {
91 unsigned int size : 8; // fill in the size of this struct
92 unsigned int valueType : 4; // type of value held by this correlation id
93 unsigned int classId : 16; // user defined classification id
94 unsigned int internalClassId : 4; // internal classification id
95
96 union {
97 blpapi_UInt64_t intValue;
98 blpapi_ManagedPtr_t ptrValue;
99 } value;
101
103int blpapi_CorrelationId_managedPtrAddRef(
104 int *numRef, blpapi_CorrelationId_t *cid);
105
107int blpapi_CorrelationId_managedPtrRelease(
108 int *numRef, blpapi_CorrelationId_t *cid);
109
110#ifdef __cplusplus
111}
112
114
115#include <cstring>
116#include <ostream>
117#include <utility>
118
126namespace BloombergLP {
127namespace blpapi {
128
129// ===================
130// class CorrelationId
131// ===================
132
207
208 enum {
210 };
211
213
214 void copy(const blpapi_CorrelationId_t& src, bool firstCopy);
215
216 template <typename TYPE>
217 static int managerFunc(blpapi_ManagedPtr_t *managedPtr,
218 const blpapi_ManagedPtr_t *srcPtr,
219 int operation);
220
221 template <typename TYPE> static void assertSmartPtrFits();
222
223 public:
224 // Possible return values for valueType() method.
225
239
240 // The maximum value allowed for classId
241
242 enum {
245 };
246
256 explicit CorrelationId(const blpapi_CorrelationId_t& correlation);
261
262 CorrelationId(const CorrelationId& original);
268 explicit CorrelationId(long long value, int classId = 0);
275 explicit CorrelationId(void *value, int classId = 0);
282 template <typename TYPE>
283 CorrelationId(const TYPE& smartPtr, void *pointerValue, int classId = 0);
298 void swap(CorrelationId& other);
311 ValueType valueType() const;
316 unsigned short classId() const;
322 void *asPointer() const;
329 template <typename TYPE> TYPE asSmartPointer() const;
337 long long asInteger() const;
346 const blpapi_CorrelationId_t& impl() const;
348};
349
353// FREE OPERATORS
354inline bool operator==(const CorrelationId& lhs, const CorrelationId& rhs);
363inline bool operator!=(const CorrelationId& lhs, const CorrelationId& rhs);
368inline bool operator<(const CorrelationId& lhs, const CorrelationId& rhs);
379//=============================================================================
380// INLINE FUNCTION DEFINITIONS
381//=============================================================================
382
383// -------------------
384// class CorrelationId
385// -------------------
386
388{
389 std::memset(&d_impl, 0, sizeof(d_impl));
390}
391
393 const blpapi_CorrelationId_t& correlationId)
394{
395 copy(correlationId, /* firstCopy = */ true);
396}
397
399{
400 copy(original.d_impl, /* firstCopy = */ false);
401}
402
403inline CorrelationId::CorrelationId(long long intValue, int newClassId)
404{
405 std::memset(&d_impl, 0, sizeof(d_impl));
406
407 d_impl.size = static_cast<unsigned>(sizeof(d_impl));
408 d_impl.valueType = INT_VALUE;
409 d_impl.value.intValue = static_cast<blpapi_UInt64_t>(intValue);
410 d_impl.classId = static_cast<unsigned>(newClassId);
411}
412
413inline CorrelationId::CorrelationId(void *ptrValue, int newClassId)
414{
415 std::memset(&d_impl, 0, sizeof(d_impl));
416
417 d_impl.size = static_cast<unsigned>(sizeof(d_impl));
418 d_impl.valueType = POINTER_VALUE;
419 d_impl.value.ptrValue.pointer = ptrValue;
420 d_impl.classId = static_cast<unsigned>(newClassId);
421}
422
423template <typename TYPE>
425 const TYPE& smartPtr, void *ptrValue, int newClassId)
426{
427 // If you get a compiler error here, the specified smart pointer does not
428 // fit in the CorrelationId and cannot be used at this time.
429
430 assertSmartPtrFits<TYPE>();
431
432 std::memset(&d_impl, 0, sizeof(d_impl));
433
434 d_impl.size = sizeof(d_impl);
435 d_impl.valueType = POINTER_VALUE;
436 d_impl.classId = newClassId;
437
438 d_impl.value.ptrValue.pointer = ptrValue;
439 d_impl.value.ptrValue.manager = &CorrelationId::managerFunc<TYPE>;
440
441 void *arena = (void *)d_impl.value.ptrValue.userData;
442 new (arena) TYPE(smartPtr);
443}
444
446{
447 if (POINTER_VALUE == valueType()) {
448 blpapi_ManagedPtr_ManagerFunction_t& manager
449 = d_impl.value.ptrValue.manager;
450 if (manager) {
451 int numRef = 0;
452 if (d_impl.internalClassId == e_FOREIGN_OBJECT
454 blpapi_CorrelationId_managedPtrRelease)
456 blpapi_CorrelationId_managedPtrRelease)(
457 &numRef, &d_impl)
458 == 0
459 && numRef > 0) {
460 return;
461 }
462 manager(&d_impl.value.ptrValue, 0, BLPAPI_MANAGEDPTR_DESTROY);
463 }
464 }
465}
466
468{
469 using std::swap;
470
471 swap(other.d_impl, d_impl);
472}
473
475{
476 CorrelationId tmp(rhs);
477 tmp.swap(*this);
478 return *this;
479}
480
481inline blpapi_CorrelationId_t& CorrelationId::impl() { return d_impl; }
482
484{
485 return (ValueType)d_impl.valueType;
486}
487
488inline unsigned short CorrelationId::classId() const { return d_impl.classId; }
489
490inline void *CorrelationId::asPointer() const
491{
492 return d_impl.value.ptrValue.pointer;
493}
494
495template <typename TYPE> inline TYPE CorrelationId::asSmartPointer() const
496{
497 typedef int (*ManagerFuncPtr)(
498 blpapi_ManagedPtr_t *, const blpapi_ManagedPtr_t *, int);
499
500 ManagerFuncPtr managerFnPtr
501 = static_cast<ManagerFuncPtr>(&(CorrelationId::managerFunc<TYPE>));
502 if (d_impl.valueType != POINTER_VALUE
503 || (d_impl.value.ptrValue.manager != managerFnPtr)) {
504 return TYPE();
505 }
506 return *(TYPE *)d_impl.value.ptrValue.userData;
507}
508
509inline long long CorrelationId::asInteger() const
510{
511 return static_cast<long long>(d_impl.value.intValue);
512}
513
514inline const blpapi_CorrelationId_t& CorrelationId::impl() const
515{
516 return d_impl;
517}
518
519inline void CorrelationId::copy(
520 const blpapi_CorrelationId_t& src, bool firstCopy)
521{
522 d_impl = src;
523
524 if (POINTER_VALUE == valueType()) {
525 blpapi_ManagedPtr_ManagerFunction_t& manager
526 = d_impl.value.ptrValue.manager;
527 if (manager) {
528 if (d_impl.internalClassId == e_FOREIGN_OBJECT) {
529 if (firstCopy) {
530 // This CorrelationId is created from a C-handle, not from
531 // another C++ CorrelationId. But this C-handle can contain
532 // a pointer to a reference counter previously created in
533 // C++ layer. It is unsafe to reuse as it might be a
534 // dangling pointer by this time. Reset userData. This
535 // allows to create a new reference counter for new C++
536 // copies of this CorrelationId.
537 std::memset(&d_impl.value.ptrValue.userData,
538 0,
539 sizeof(d_impl.value.ptrValue.userData));
540 }
541 int numRef = 0;
543 BLPAPI_CALL(blpapi_CorrelationId_managedPtrAddRef)(
544 &numRef, &d_impl));
545 if (numRef > 1) {
546 return;
547 }
548 }
549 manager(&d_impl.value.ptrValue,
550 &src.value.ptrValue,
552 }
553 }
554}
555
556template <typename TYPE>
557inline int CorrelationId::managerFunc(blpapi_ManagedPtr_t *managedPtr,
558 const blpapi_ManagedPtr_t *srcPtr,
559 int operation)
560{
561 if (operation == BLPAPI_MANAGEDPTR_COPY) {
562 managedPtr->pointer = srcPtr->pointer;
563 managedPtr->manager = srcPtr->manager;
564
565 void *arena = managedPtr->userData;
566 new (arena) TYPE(*((TYPE *)&srcPtr->userData[0]));
567 } else if (operation == BLPAPI_MANAGEDPTR_DESTROY) {
568 TYPE *managedPtr_p = (TYPE *)&managedPtr->userData[0];
569 managedPtr_p->~TYPE();
570 } else if (operation == BLPAPI_MANAGEDPTR_IMPOSSIBLE_OPERATION) {
571 static int uniquePerTemplateInstantiation;
572
573 const int *address = &uniquePerTemplateInstantiation;
574 int rc = 0;
575 std::memcpy(&rc, &address, std::min(sizeof address, sizeof rc));
576 return rc;
577 // Instantiations of this function template, 'managerFunc<TYPE>',
578 // will never be called with 'operation' equal to
579 // 'BLPAPI_MANAGEDPTR_IMPOSSIBLE_OPERATION': this branch will never
580 // be executed.
581 //
582 // The observable use of the address of a local static variable
583 // forces '&managerFunc<T1> != &managerFunc<T2>' for types
584 // 'T1 != T2' even in the presence of Visual C++'s "identical
585 // COMDAT folding" optimization.
586 }
587
588 return 0;
589}
590
591template <typename TYPE> inline void CorrelationId::assertSmartPtrFits()
592{
593 if (false) {
594 // If you get a compiler error here, the specified smart pointer does
595 // not fit in the CorrelationId and cannot be used at this time.
596
597 char errorIfSmartPtrDoesNotFit[sizeof(TYPE) <= (sizeof(void *) * 4)
598 ? 1
599 : -1];
600 (void)errorIfSmartPtrDoesNotFit;
601 }
602}
603
604inline bool operator==(const CorrelationId& lhs, const CorrelationId& rhs)
605{
606 if (lhs.valueType() != rhs.valueType()) {
607 return false;
608 }
609 if (lhs.classId() != rhs.classId()) {
610 return false;
611 }
612 if (lhs.impl().internalClassId != rhs.impl().internalClassId) {
613 return false;
614 }
615
617 if (lhs.asPointer() != rhs.asPointer()) {
618 return false;
619 }
620 } else if (lhs.asInteger() != rhs.asInteger()) {
621 return false;
622 }
623
624 return true;
625}
626
627inline bool operator!=(const CorrelationId& lhs, const CorrelationId& rhs)
628{
629 return !(lhs == rhs);
630}
631
632inline bool operator<(const CorrelationId& lhs, const CorrelationId& rhs)
633{
635 && lhs.impl().internalClassId
638 && rhs.impl().internalClassId
640 return lhs.classId() == rhs.classId()
641 ? lhs.asPointer() < rhs.asPointer()
642 : lhs.classId() < rhs.classId();
643 }
644 return std::memcmp(&lhs.impl(), &rhs.impl(), sizeof(rhs.impl())) < 0;
645}
646
647inline std::ostream& operator<<(
648 std::ostream& os, const CorrelationId& correlator)
649{
650 const char *valueType = 0;
651 switch (correlator.valueType()) {
653 valueType = "UNSET";
654 break;
656 valueType = "INT";
657 break;
659 valueType = "POINTER";
660 break;
662 valueType = "AUTOGEN";
663 break;
664 default:
665 valueType = "UNKNOWN";
666 }
667
668 os << "[ valueType=" << valueType << " classId=" << correlator.classId()
669 << " internalClassId=" << correlator.impl().internalClassId
670 << " value=";
671
672 if (correlator.valueType() == CorrelationId::POINTER_VALUE) {
673 os << correlator.asPointer();
674 } else {
675 os << correlator.asInteger();
676 }
677 os << " ]";
678
679 return os;
680}
681
682} // close namespace blpapi
683} // close namespace BloombergLP
684
685#endif // #ifdef __cplusplus
686#endif // #ifndef INCLUDED_BLPAPI_CORRELATIONID
Provide functions for dispatchtbl.
#define BLPAPI_CALL_UNCHECKED(FUNCNAME)
Definition blpapi_call.h:354
#define BLPAPI_CALL_AVAILABLE(FUNCNAME)
Definition blpapi_call.h:352
#define BLPAPI_CALL(FUNCNAME)
Definition blpapi_call.h:353
Common definitions used by the library.
#define BLPAPI_CORRELATION_TYPE_AUTOGEN
Definition blpapi_defs.h:54
#define BLPAPI_CORRELATION_INTERNAL_CLASS_FOREIGN_OBJECT
Definition blpapi_defs.h:56
#define BLPAPI_CORRELATION_TYPE_POINTER
Definition blpapi_defs.h:53
#define BLPAPI_MANAGEDPTR_IMPOSSIBLE_OPERATION
Definition blpapi_defs.h:60
#define BLPAPI_CORRELATION_TYPE_UNSET
Definition blpapi_defs.h:51
#define BLPAPI_CORRELATION_MAX_CLASS_ID
Definition blpapi_defs.h:55
#define BLPAPI_EXPORT
Definition blpapi_defs.h:172
#define BLPAPI_MANAGEDPTR_DESTROY
Definition blpapi_defs.h:59
#define BLPAPI_CORRELATION_TYPE_INT
Definition blpapi_defs.h:52
#define BLPAPI_MANAGEDPTR_COPY
Definition blpapi_defs.h:58
struct blpapi_CorrelationId_t_ blpapi_CorrelationId_t
Definition blpapi_dispatchtbl.h:74
Defines Exceptions that can be thrown by the blpapi library.
Provide BLPAPI types.
unsigned long long blpapi_UInt64_t
Definition blpapi_types.h:70
Definition blpapi_correlationid.h:206
void swap(CorrelationId &other)
Definition blpapi_correlationid.h:467
unsigned short classId() const
Definition blpapi_correlationid.h:488
ValueType valueType() const
Definition blpapi_correlationid.h:483
void * asPointer() const
Definition blpapi_correlationid.h:490
TYPE asSmartPointer() const
Definition blpapi_correlationid.h:495
~CorrelationId()
Definition blpapi_correlationid.h:445
CorrelationId()
Definition blpapi_correlationid.h:387
long long asInteger() const
Definition blpapi_correlationid.h:509
ValueType
Definition blpapi_correlationid.h:226
@ AUTOGEN_VALUE
The CorrelationId was created internally by API.
Definition blpapi_correlationid.h:236
@ UNSET_VALUE
Definition blpapi_correlationid.h:227
@ INT_VALUE
Definition blpapi_correlationid.h:230
@ POINTER_VALUE
Definition blpapi_correlationid.h:233
@ MAX_CLASS_ID
Definition blpapi_correlationid.h:243
CorrelationId & operator=(const CorrelationId &rhs)
Definition blpapi_correlationid.h:474
static void throwOnError(int errorCode)
Definition blpapi_exception.h:526
bool operator==(const CorrelationId &lhs, const CorrelationId &rhs)
Definition blpapi_correlationid.h:604
std::ostream & operator<<(std::ostream &os, const CorrelationId &correlator)
Definition blpapi_correlationid.h:647
bool operator!=(const CorrelationId &lhs, const CorrelationId &rhs)
Definition blpapi_correlationid.h:627
bool operator<(const CorrelationId &lhs, const CorrelationId &rhs)
Definition blpapi_correlationid.h:632
Definition blpapi_abstractsession.h:195