12 #ifndef hifi_SharedUtil_h
13 #define hifi_SharedUtil_h
24 #include <QtCore/QDebug>
25 #include <QtCore/QCoreApplication>
28 #include "NumericalConstants.h"
31 const QUuid AVATAR_SELF_ID = QUuid(
"{00000000-0000-0000-0000-000000000001}");
35 std::unique_ptr<T>& globalInstancePointer() {
36 static std::unique_ptr<T> instancePtr;
44 void setupGlobalInstances();
46 std::mutex& globalInstancesMutex();
47 QVariant getGlobalInstance(
const char* propertyName);
48 void setGlobalInstance(
const char* propertyName,
const QVariant& variant);
53 template <
typename T,
typename... Args>
54 T* globalInstance(
const char* propertyName, Args&&... args) {
55 static T* resultInstance {
nullptr };
56 if (!resultInstance) {
57 std::unique_lock<std::mutex> lock(globalInstancesMutex());
58 if (!resultInstance) {
59 auto variant = getGlobalInstance(propertyName);
60 if (variant.isNull()) {
61 std::unique_ptr<T>& instancePtr = globalInstancePointer<T>();
62 if (!instancePtr.get()) {
65 instancePtr = std::unique_ptr<T>(
new T(std::forward<Args>(args)...));
67 void* voidInstance = &(*instancePtr);
68 variant = QVariant::fromValue(voidInstance);
69 setGlobalInstance(propertyName, variant);
71 void* returnedVoidInstance = variant.value<
void*>();
72 resultInstance =
static_cast<T*
>(returnedVoidInstance);
75 return resultInstance;
79 const int BYTES_PER_COLOR = 3;
80 const int BYTES_PER_FLAGS = 1;
81 typedef unsigned char colorPart;
82 typedef unsigned char nodeColor[BYTES_PER_COLOR + BYTES_PER_FLAGS];
85 quint64 usecTimestampNow(
bool wantDebug =
false);
86 void usecTimestampNowForceClockSkew(qint64 clockSkew);
88 inline bool afterUsecs(quint64& startUsecs, quint64 maxIntervalUecs) {
89 auto now = usecTimestampNow();
90 auto interval = now - startUsecs;
91 if (interval > maxIntervalUecs) {
98 inline bool afterSecs(quint64& startUsecs, quint64 maxIntervalSecs) {
99 return afterUsecs(startUsecs, maxIntervalSecs * USECS_PER_SECOND);
102 template <
typename F>
103 void doEvery(quint64& lastReportUsecs, quint64 secs, F lamdba) {
104 if (afterSecs(lastReportUsecs, secs)) {
111 float secTimestampNow();
114 struct LaterDeleter {
115 void operator()(QObject* ptr) {
121 int randIntInRange (
int min,
int max);
122 float randFloatInRange (
float min,
float max);
124 unsigned char randomColorValue(
int minimum = 0);
125 bool randomBoolean();
127 bool shouldDo(
float desiredInterval,
float deltaTime);
129 void outputBufferBits(
const unsigned char* buffer,
int length, QDebug* continuedDebug = NULL);
130 void outputBits(
unsigned char byte, QDebug* continuedDebug = NULL);
131 void printVoxelCode(
unsigned char* voxelCode);
132 int numberOfOnes(
unsigned char byte);
133 bool oneAtBit(
unsigned char byte,
int bitIndex);
134 void setAtBit(
unsigned char&
byte,
int bitIndex);
135 bool oneAtBit16(
unsigned short word,
int bitIndex);
136 void setAtBit16(
unsigned short& word,
int bitIndex);
137 void clearAtBit(
unsigned char&
byte,
int bitIndex);
138 int getSemiNibbleAt(
unsigned short word,
int bitIndex);
139 void setSemiNibbleAt(
unsigned short& word,
int bitIndex,
int value);
141 int getNthBit(
unsigned char byte,
int ordinal);
143 bool isInEnvironment(
const char* environment);
145 const char* getCmdOption(
int argc,
const char * argv[],
const char* option);
146 bool cmdOptionExists(
int argc,
const char * argv[],
const char* option);
148 void sharedMessageHandler(QtMsgType type,
const QMessageLogContext& context,
const QString &message);
150 unsigned char* pointToVoxel(
float x,
float y,
float z,
float s,
unsigned char r = 0,
unsigned char g = 0,
unsigned char b = 0);
151 unsigned char* pointToOctalCode(
float x,
float y,
float z,
float s);
154 void usleep(
int waitTime);
157 int insertIntoSortedArrays(
void* value,
float key,
int originalIndex,
158 void** valueArray,
float* keyArray,
int* originalIndexArray,
159 int currentCount,
int maxCount);
161 int removeFromSortedArrays(
void* value,
void** valueArray,
float* keyArray,
int* originalIndexArray,
162 int currentCount,
int maxCount);
167 static const char* valueOf(
bool checkValue) {
return checkValue ?
"yes" :
"no"; }
168 static void setDeadBeef(
void* memoryVoid,
int size);
169 static void checkDeadBeef(
void* memoryVoid,
int size);
171 static unsigned char DEADBEEF[];
172 static int DEADBEEF_SIZE;
176 inline bool isBetween(int64_t value, int64_t max, int64_t min) {
return ((value <= max) && (value >= min)); }
179 inline bool isNaN(
float value) {
return value != value; }
181 QString formatUsecTime(
float usecs);
182 QString formatUsecTime(
double usecs);
183 QString formatUsecTime(quint64 usecs);
184 QString formatUsecTime(qint64 usecs);
185 QString formatSecTime(qint64 secs);
187 QString formatSecondsElapsed(
float seconds);
188 bool similarStrings(
const QString& stringA,
const QString& stringB);
190 template <
typename T>
191 uint qHash(
const std::shared_ptr<T>& ptr, uint seed = 0)
193 return qHash(ptr.get(), seed);
196 void disableQtBearerPoll();
198 void printSystemInformation();
201 uint64_t totalMemoryBytes;
202 uint64_t availMemoryBytes;
203 uint64_t usedMemoryBytes;
204 uint64_t processUsedMemoryBytes;
205 uint64_t processPeakUsedMemoryBytes;
208 bool getMemoryInfo(MemoryInfo& info);
210 struct ProcessorInfo {
211 int32_t numPhysicalProcessorPackages;
212 int32_t numProcessorCores;
213 int32_t numLogicalProcessors;
214 int32_t numProcessorCachesL1;
215 int32_t numProcessorCachesL2;
216 int32_t numProcessorCachesL3;
219 bool getProcessorInfo(ProcessorInfo& info);
221 const QString& getInterfaceSharedMemoryName();
223 void setMaxCores(uint8_t maxCores);
225 const QString PARENT_PID_OPTION =
"parent-pid";
226 void watchParentProcess(
int parentPID);
228 bool processIsRunning(int64_t pid);
230 void setupHifiApplication(QString applicationName);
233 void* createProcessGroup();
234 void addProcessToGroup(
void* processGroup, qint64 processId);