mirror of
https://github.com/overte-org/overte.git
synced 2025-08-08 09:57:26 +02:00
Merge branch 'master' of https://github.com/highfidelity/hifi into temp1
This commit is contained in:
commit
7aaac69d35
29 changed files with 362 additions and 272 deletions
|
@ -16,7 +16,7 @@
|
||||||
#include <AccountManager.h>
|
#include <AccountManager.h>
|
||||||
#include <Assignment.h>
|
#include <Assignment.h>
|
||||||
#include <HifiConfigVariantMap.h>
|
#include <HifiConfigVariantMap.h>
|
||||||
#include <Logging.h>
|
#include <LogHandler.h>
|
||||||
#include <LogUtils.h>
|
#include <LogUtils.h>
|
||||||
#include <NodeList.h>
|
#include <NodeList.h>
|
||||||
#include <PacketHeaders.h>
|
#include <PacketHeaders.h>
|
||||||
|
@ -51,7 +51,7 @@ AssignmentClient::AssignmentClient(int &argc, char **argv) :
|
||||||
connect(&_shutdownEventListener, SIGNAL(receivedCloseEvent()), SLOT(quit()));
|
connect(&_shutdownEventListener, SIGNAL(receivedCloseEvent()), SLOT(quit()));
|
||||||
|
|
||||||
// set the logging target to the the CHILD_TARGET_NAME
|
// set the logging target to the the CHILD_TARGET_NAME
|
||||||
Logging::setTargetName(ASSIGNMENT_CLIENT_TARGET_NAME);
|
LogHandler::getInstance().setTargetName(ASSIGNMENT_CLIENT_TARGET_NAME);
|
||||||
|
|
||||||
const QVariantMap argumentVariantMap = HifiConfigVariantMap::mergeCLParametersWithJSONConfig(arguments());
|
const QVariantMap argumentVariantMap = HifiConfigVariantMap::mergeCLParametersWithJSONConfig(arguments());
|
||||||
|
|
||||||
|
@ -218,7 +218,7 @@ void AssignmentClient::handleAuthenticationRequest() {
|
||||||
|
|
||||||
void AssignmentClient::assignmentCompleted() {
|
void AssignmentClient::assignmentCompleted() {
|
||||||
// reset the logging target to the the CHILD_TARGET_NAME
|
// reset the logging target to the the CHILD_TARGET_NAME
|
||||||
Logging::setTargetName(ASSIGNMENT_CLIENT_TARGET_NAME);
|
LogHandler::getInstance().setTargetName(ASSIGNMENT_CLIENT_TARGET_NAME);
|
||||||
|
|
||||||
qDebug("Assignment finished or never started - waiting for new assignment.");
|
qDebug("Assignment finished or never started - waiting for new assignment.");
|
||||||
|
|
||||||
|
|
|
@ -9,7 +9,7 @@
|
||||||
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
//
|
//
|
||||||
|
|
||||||
#include <Logging.h>
|
#include <LogHandler.h>
|
||||||
|
|
||||||
#include "AssignmentClientMonitor.h"
|
#include "AssignmentClientMonitor.h"
|
||||||
|
|
||||||
|
@ -21,7 +21,7 @@ AssignmentClientMonitor::AssignmentClientMonitor(int &argc, char **argv, int num
|
||||||
QCoreApplication(argc, argv)
|
QCoreApplication(argc, argv)
|
||||||
{
|
{
|
||||||
// start the Logging class with the parent's target name
|
// start the Logging class with the parent's target name
|
||||||
Logging::setTargetName(ASSIGNMENT_CLIENT_MONITOR_TARGET_NAME);
|
LogHandler::getInstance().setTargetName(ASSIGNMENT_CLIENT_MONITOR_TARGET_NAME);
|
||||||
|
|
||||||
_childArguments = arguments();
|
_childArguments = arguments();
|
||||||
|
|
||||||
|
|
|
@ -41,7 +41,7 @@
|
||||||
#include <QtNetwork/QNetworkRequest>
|
#include <QtNetwork/QNetworkRequest>
|
||||||
#include <QtNetwork/QNetworkReply>
|
#include <QtNetwork/QNetworkReply>
|
||||||
|
|
||||||
#include <Logging.h>
|
#include <LogHandler.h>
|
||||||
#include <NetworkAccessManager.h>
|
#include <NetworkAccessManager.h>
|
||||||
#include <NodeList.h>
|
#include <NodeList.h>
|
||||||
#include <Node.h>
|
#include <Node.h>
|
||||||
|
@ -640,6 +640,7 @@ void AudioMixer::run() {
|
||||||
timer.start();
|
timer.start();
|
||||||
|
|
||||||
char clientMixBuffer[MAX_PACKET_SIZE];
|
char clientMixBuffer[MAX_PACKET_SIZE];
|
||||||
|
char clientEnvBuffer[MAX_PACKET_SIZE];
|
||||||
|
|
||||||
int usecToSleep = BUFFER_SEND_INTERVAL_USECS;
|
int usecToSleep = BUFFER_SEND_INTERVAL_USECS;
|
||||||
|
|
||||||
|
@ -719,65 +720,90 @@ void AudioMixer::run() {
|
||||||
|
|
||||||
int streamsMixed = prepareMixForListeningNode(node.data());
|
int streamsMixed = prepareMixForListeningNode(node.data());
|
||||||
|
|
||||||
char* dataAt;
|
char* mixDataAt;
|
||||||
if (streamsMixed > 0) {
|
if (streamsMixed > 0) {
|
||||||
// pack header
|
// pack header
|
||||||
int numBytesPacketHeader = populatePacketHeader(clientMixBuffer, PacketTypeMixedAudio);
|
int numBytesMixPacketHeader = populatePacketHeader(clientMixBuffer, PacketTypeMixedAudio);
|
||||||
dataAt = clientMixBuffer + numBytesPacketHeader;
|
mixDataAt = clientMixBuffer + numBytesMixPacketHeader;
|
||||||
|
|
||||||
// pack sequence number
|
// pack sequence number
|
||||||
quint16 sequence = nodeData->getOutgoingSequenceNumber();
|
quint16 sequence = nodeData->getOutgoingSequenceNumber();
|
||||||
memcpy(dataAt, &sequence, sizeof(quint16));
|
memcpy(mixDataAt, &sequence, sizeof(quint16));
|
||||||
dataAt += sizeof(quint16);
|
mixDataAt += sizeof(quint16);
|
||||||
|
|
||||||
|
// pack mixed audio samples
|
||||||
|
memcpy(mixDataAt, _mixSamples, NETWORK_BUFFER_LENGTH_BYTES_STEREO);
|
||||||
|
mixDataAt += NETWORK_BUFFER_LENGTH_BYTES_STEREO;
|
||||||
|
|
||||||
// Pack stream properties
|
// Send stream properties
|
||||||
bool inAZone = false;
|
bool hasReverb = false;
|
||||||
|
float reverbTime, wetLevel;
|
||||||
|
// find reverb properties
|
||||||
for (int i = 0; i < _zoneReverbSettings.size(); ++i) {
|
for (int i = 0; i < _zoneReverbSettings.size(); ++i) {
|
||||||
AudioMixerClientData* data = static_cast<AudioMixerClientData*>(node->getLinkedData());
|
AudioMixerClientData* data = static_cast<AudioMixerClientData*>(node->getLinkedData());
|
||||||
glm::vec3 streamPosition = data->getAvatarAudioStream()->getPosition();
|
glm::vec3 streamPosition = data->getAvatarAudioStream()->getPosition();
|
||||||
if (_audioZones[_zoneReverbSettings[i].zone].contains(streamPosition)) {
|
if (_audioZones[_zoneReverbSettings[i].zone].contains(streamPosition)) {
|
||||||
bool hasReverb = true;
|
hasReverb = true;
|
||||||
float reverbTime = _zoneReverbSettings[i].reverbTime;
|
reverbTime = _zoneReverbSettings[i].reverbTime;
|
||||||
float wetLevel = _zoneReverbSettings[i].wetLevel;
|
wetLevel = _zoneReverbSettings[i].wetLevel;
|
||||||
|
|
||||||
memcpy(dataAt, &hasReverb, sizeof(bool));
|
|
||||||
dataAt += sizeof(bool);
|
|
||||||
memcpy(dataAt, &reverbTime, sizeof(float));
|
|
||||||
dataAt += sizeof(float);
|
|
||||||
memcpy(dataAt, &wetLevel, sizeof(float));
|
|
||||||
dataAt += sizeof(float);
|
|
||||||
|
|
||||||
inAZone = true;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (!inAZone) {
|
AvatarAudioStream* stream = nodeData->getAvatarAudioStream();
|
||||||
bool hasReverb = false;
|
bool dataChanged = (stream->hasReverb() != hasReverb) ||
|
||||||
memcpy(dataAt, &hasReverb, sizeof(bool));
|
(stream->hasReverb() && (stream->getRevebTime() != reverbTime ||
|
||||||
dataAt += sizeof(bool);
|
stream->getWetLevel() != wetLevel));
|
||||||
|
if (dataChanged) {
|
||||||
|
// Update stream
|
||||||
|
if (hasReverb) {
|
||||||
|
stream->setReverb(reverbTime, wetLevel);
|
||||||
|
} else {
|
||||||
|
stream->clearReverb();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// pack mixed audio samples
|
// Send at change or every so often
|
||||||
memcpy(dataAt, _mixSamples, NETWORK_BUFFER_LENGTH_BYTES_STEREO);
|
float CHANCE_OF_SEND = 0.01f;
|
||||||
dataAt += NETWORK_BUFFER_LENGTH_BYTES_STEREO;
|
bool sendData = dataChanged || (randFloat() < CHANCE_OF_SEND);
|
||||||
|
|
||||||
|
if (sendData) {
|
||||||
|
int numBytesEnvPacketHeader = populatePacketHeader(clientEnvBuffer, PacketTypeAudioEnvironment);
|
||||||
|
char* envDataAt = clientEnvBuffer + numBytesEnvPacketHeader;
|
||||||
|
|
||||||
|
unsigned char bitset = 0;
|
||||||
|
if (hasReverb) {
|
||||||
|
setAtBit(bitset, HAS_REVERB_BIT);
|
||||||
|
}
|
||||||
|
|
||||||
|
memcpy(envDataAt, &bitset, sizeof(unsigned char));
|
||||||
|
envDataAt += sizeof(unsigned char);
|
||||||
|
|
||||||
|
if (hasReverb) {
|
||||||
|
memcpy(envDataAt, &reverbTime, sizeof(float));
|
||||||
|
envDataAt += sizeof(float);
|
||||||
|
memcpy(envDataAt, &wetLevel, sizeof(float));
|
||||||
|
envDataAt += sizeof(float);
|
||||||
|
}
|
||||||
|
nodeList->writeDatagram(clientEnvBuffer, envDataAt - clientEnvBuffer, node);
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
// pack header
|
// pack header
|
||||||
int numBytesPacketHeader = populatePacketHeader(clientMixBuffer, PacketTypeSilentAudioFrame);
|
int numBytesPacketHeader = populatePacketHeader(clientMixBuffer, PacketTypeSilentAudioFrame);
|
||||||
dataAt = clientMixBuffer + numBytesPacketHeader;
|
mixDataAt = clientMixBuffer + numBytesPacketHeader;
|
||||||
|
|
||||||
// pack sequence number
|
// pack sequence number
|
||||||
quint16 sequence = nodeData->getOutgoingSequenceNumber();
|
quint16 sequence = nodeData->getOutgoingSequenceNumber();
|
||||||
memcpy(dataAt, &sequence, sizeof(quint16));
|
memcpy(mixDataAt, &sequence, sizeof(quint16));
|
||||||
dataAt += sizeof(quint16);
|
mixDataAt += sizeof(quint16);
|
||||||
|
|
||||||
// pack number of silent audio samples
|
// pack number of silent audio samples
|
||||||
quint16 numSilentSamples = NETWORK_BUFFER_LENGTH_SAMPLES_STEREO;
|
quint16 numSilentSamples = NETWORK_BUFFER_LENGTH_SAMPLES_STEREO;
|
||||||
memcpy(dataAt, &numSilentSamples, sizeof(quint16));
|
memcpy(mixDataAt, &numSilentSamples, sizeof(quint16));
|
||||||
dataAt += sizeof(quint16);
|
mixDataAt += sizeof(quint16);
|
||||||
}
|
}
|
||||||
|
|
||||||
// send mixed audio packet
|
// send mixed audio packet
|
||||||
nodeList->writeDatagram(clientMixBuffer, dataAt - clientMixBuffer, node);
|
nodeList->writeDatagram(clientMixBuffer, mixDataAt - clientMixBuffer, node);
|
||||||
nodeData->incrementOutgoingMixedAudioSequenceNumber();
|
nodeData->incrementOutgoingMixedAudioSequenceNumber();
|
||||||
|
|
||||||
// send an audio stream stats packet if it's time
|
// send an audio stream stats packet if it's time
|
||||||
|
|
|
@ -15,7 +15,7 @@
|
||||||
#include <QtCore/QTimer>
|
#include <QtCore/QTimer>
|
||||||
#include <QtCore/QThread>
|
#include <QtCore/QThread>
|
||||||
|
|
||||||
#include <Logging.h>
|
#include <LogHandler.h>
|
||||||
#include <NodeList.h>
|
#include <NodeList.h>
|
||||||
#include <PacketHeaders.h>
|
#include <PacketHeaders.h>
|
||||||
#include <SharedUtil.h>
|
#include <SharedUtil.h>
|
||||||
|
|
|
@ -9,7 +9,7 @@
|
||||||
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
//
|
//
|
||||||
|
|
||||||
#include <Logging.h>
|
#include <LogHandler.h>
|
||||||
#include <SharedUtil.h>
|
#include <SharedUtil.h>
|
||||||
|
|
||||||
#include "Assignment.h"
|
#include "Assignment.h"
|
||||||
|
@ -22,7 +22,7 @@ int main(int argc, char* argv[]) {
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// use the verbose message handler in Logging
|
// use the verbose message handler in Logging
|
||||||
qInstallMessageHandler(Logging::verboseMessageHandler);
|
qInstallMessageHandler(LogHandler::verboseMessageHandler);
|
||||||
|
|
||||||
const char* numForksString = getCmdOption(argc, (const char**)argv, NUM_FORKS_PARAMETER);
|
const char* numForksString = getCmdOption(argc, (const char**)argv, NUM_FORKS_PARAMETER);
|
||||||
|
|
||||||
|
|
|
@ -18,7 +18,7 @@
|
||||||
|
|
||||||
#include <AccountManager.h>
|
#include <AccountManager.h>
|
||||||
#include <HTTPConnection.h>
|
#include <HTTPConnection.h>
|
||||||
#include <Logging.h>
|
#include <LogHandler.h>
|
||||||
#include <UUID.h>
|
#include <UUID.h>
|
||||||
|
|
||||||
#include "../AssignmentClient.h"
|
#include "../AssignmentClient.h"
|
||||||
|
@ -923,7 +923,7 @@ void OctreeServer::run() {
|
||||||
|
|
||||||
beforeRun(); // after payload has been processed
|
beforeRun(); // after payload has been processed
|
||||||
|
|
||||||
qInstallMessageHandler(Logging::verboseMessageHandler);
|
qInstallMessageHandler(LogHandler::verboseMessageHandler);
|
||||||
|
|
||||||
const char* STATUS_PORT = "--statusPort";
|
const char* STATUS_PORT = "--statusPort";
|
||||||
const char* statusPort = getCmdOption(_argc, _argv, STATUS_PORT);
|
const char* statusPort = getCmdOption(_argc, _argv, STATUS_PORT);
|
||||||
|
|
|
@ -17,7 +17,7 @@
|
||||||
|
|
||||||
#include <QtCore/QCoreApplication>
|
#include <QtCore/QCoreApplication>
|
||||||
|
|
||||||
#include <Logging.h>
|
#include <LogHandler.h>
|
||||||
#include <SharedUtil.h>
|
#include <SharedUtil.h>
|
||||||
|
|
||||||
#include "DomainServer.h"
|
#include "DomainServer.h"
|
||||||
|
@ -27,7 +27,7 @@ int main(int argc, char* argv[]) {
|
||||||
setvbuf(stdout, NULL, _IOLBF, 0);
|
setvbuf(stdout, NULL, _IOLBF, 0);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
qInstallMessageHandler(Logging::verboseMessageHandler);
|
qInstallMessageHandler(LogHandler::verboseMessageHandler);
|
||||||
|
|
||||||
int currentExitCode = 0;
|
int currentExitCode = 0;
|
||||||
|
|
||||||
|
|
|
@ -11,7 +11,7 @@
|
||||||
|
|
||||||
#include <QtCore/QCoreApplication>
|
#include <QtCore/QCoreApplication>
|
||||||
|
|
||||||
#include <Logging.h>
|
#include <LogHandler.h>
|
||||||
|
|
||||||
#include "IceServer.h"
|
#include "IceServer.h"
|
||||||
|
|
||||||
|
@ -20,7 +20,7 @@ int main(int argc, char* argv[]) {
|
||||||
setvbuf(stdout, NULL, _IOLBF, 0);
|
setvbuf(stdout, NULL, _IOLBF, 0);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
qInstallMessageHandler(Logging::verboseMessageHandler);
|
qInstallMessageHandler(LogHandler::verboseMessageHandler);
|
||||||
|
|
||||||
IceServer iceServer(argc, argv);
|
IceServer iceServer(argc, argv);
|
||||||
return iceServer.exec();
|
return iceServer.exec();
|
||||||
|
|
2
interface/external/gverb/readme.txt
vendored
2
interface/external/gverb/readme.txt
vendored
|
@ -1,7 +1,7 @@
|
||||||
|
|
||||||
Instructions for adding the Gverb library to Interface
|
Instructions for adding the Gverb library to Interface
|
||||||
(This is a required library)
|
(This is a required library)
|
||||||
Clément Brisset, Octobre 22nd, 2014
|
Clément Brisset, October 22nd, 2014
|
||||||
|
|
||||||
1. Go to https://github.com/highfidelity/gverb
|
1. Go to https://github.com/highfidelity/gverb
|
||||||
Or download the sources directly via this link:
|
Or download the sources directly via this link:
|
||||||
|
|
|
@ -58,7 +58,7 @@
|
||||||
#include <HFActionEvent.h>
|
#include <HFActionEvent.h>
|
||||||
#include <HFBackEvent.h>
|
#include <HFBackEvent.h>
|
||||||
#include <LocalVoxelsList.h>
|
#include <LocalVoxelsList.h>
|
||||||
#include <Logging.h>
|
#include <LogHandler.h>
|
||||||
#include <NetworkAccessManager.h>
|
#include <NetworkAccessManager.h>
|
||||||
#include <OctalCode.h>
|
#include <OctalCode.h>
|
||||||
#include <OctreeSceneStats.h>
|
#include <OctreeSceneStats.h>
|
||||||
|
@ -116,12 +116,10 @@ const QString SKIP_FILENAME = QStandardPaths::writableLocation(QStandardPaths::D
|
||||||
const QString DEFAULT_SCRIPTS_JS_URL = "http://public.highfidelity.io/scripts/defaultScripts.js";
|
const QString DEFAULT_SCRIPTS_JS_URL = "http://public.highfidelity.io/scripts/defaultScripts.js";
|
||||||
|
|
||||||
void messageHandler(QtMsgType type, const QMessageLogContext& context, const QString& message) {
|
void messageHandler(QtMsgType type, const QMessageLogContext& context, const QString& message) {
|
||||||
if (message.size() > 0) {
|
QString logMessage = LogHandler::getInstance().printMessage((LogMsgType) type, context, message);
|
||||||
QString dateString = QDateTime::currentDateTime().toTimeSpec(Qt::LocalTime).toString(Qt::ISODate);
|
|
||||||
QString formattedMessage = QString("[%1] %2\n").arg(dateString).arg(message);
|
if (!logMessage.isEmpty()) {
|
||||||
|
Application::getInstance()->getLogger()->addMessage(qPrintable(logMessage));
|
||||||
fprintf(stdout, "%s", qPrintable(formattedMessage));
|
|
||||||
Application::getInstance()->getLogger()->addMessage(qPrintable(formattedMessage));
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -581,10 +579,6 @@ void Application::initializeGL() {
|
||||||
float startupTime = (float)_applicationStartupTime.elapsed() / 1000.0;
|
float startupTime = (float)_applicationStartupTime.elapsed() / 1000.0;
|
||||||
_justStarted = false;
|
_justStarted = false;
|
||||||
qDebug("Startup time: %4.2f seconds.", startupTime);
|
qDebug("Startup time: %4.2f seconds.", startupTime);
|
||||||
const char LOGSTASH_INTERFACE_START_TIME_KEY[] = "interface-start-time";
|
|
||||||
|
|
||||||
// ask the Logstash class to record the startup time
|
|
||||||
Logging::stashValue(STAT_TYPE_TIMER, LOGSTASH_INTERFACE_START_TIME_KEY, startupTime);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// update before the first render
|
// update before the first render
|
||||||
|
|
|
@ -1018,6 +1018,27 @@ void Audio::parseAudioStreamStatsPacket(const QByteArray& packet) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Audio::parseAudioEnvironmentData(const QByteArray &packet) {
|
||||||
|
int numBytesPacketHeader = numBytesForPacketHeader(packet);
|
||||||
|
const char* dataAt = packet.constData() + numBytesPacketHeader;
|
||||||
|
|
||||||
|
char bitset;
|
||||||
|
memcpy(&bitset, dataAt, sizeof(char));
|
||||||
|
dataAt += sizeof(char);
|
||||||
|
|
||||||
|
bool hasReverb = oneAtBit(bitset, HAS_REVERB_BIT);;
|
||||||
|
if (hasReverb) {
|
||||||
|
float reverbTime, wetLevel;
|
||||||
|
memcpy(&reverbTime, dataAt, sizeof(float));
|
||||||
|
dataAt += sizeof(float);
|
||||||
|
memcpy(&wetLevel, dataAt, sizeof(float));
|
||||||
|
dataAt += sizeof(float);
|
||||||
|
_receivedAudioStream.setReverb(reverbTime, wetLevel);
|
||||||
|
} else {
|
||||||
|
_receivedAudioStream.clearReverb();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void Audio::sendDownstreamAudioStatsPacket() {
|
void Audio::sendDownstreamAudioStatsPacket() {
|
||||||
|
|
||||||
// since this function is called every second, we'll sample for some of our stats here
|
// since this function is called every second, we'll sample for some of our stats here
|
||||||
|
|
|
@ -125,6 +125,7 @@ public slots:
|
||||||
void stop();
|
void stop();
|
||||||
void addReceivedAudioToStream(const QByteArray& audioByteArray);
|
void addReceivedAudioToStream(const QByteArray& audioByteArray);
|
||||||
void parseAudioStreamStatsPacket(const QByteArray& packet);
|
void parseAudioStreamStatsPacket(const QByteArray& packet);
|
||||||
|
void parseAudioEnvironmentData(const QByteArray& packet);
|
||||||
void addSpatialAudioToBuffer(unsigned int sampleTime, const QByteArray& spatialAudio, unsigned int numSamples);
|
void addSpatialAudioToBuffer(unsigned int sampleTime, const QByteArray& spatialAudio, unsigned int numSamples);
|
||||||
void handleAudioInput();
|
void handleAudioInput();
|
||||||
void reset();
|
void reset();
|
||||||
|
|
|
@ -49,14 +49,18 @@ void DatagramProcessor::processDatagrams() {
|
||||||
PacketType incomingType = packetTypeForPacket(incomingPacket);
|
PacketType incomingType = packetTypeForPacket(incomingPacket);
|
||||||
// only process this packet if we have a match on the packet version
|
// only process this packet if we have a match on the packet version
|
||||||
switch (incomingType) {
|
switch (incomingType) {
|
||||||
|
case PacketTypeAudioEnvironment:
|
||||||
|
case PacketTypeAudioStreamStats:
|
||||||
case PacketTypeMixedAudio:
|
case PacketTypeMixedAudio:
|
||||||
case PacketTypeSilentAudioFrame:
|
case PacketTypeSilentAudioFrame: {
|
||||||
case PacketTypeAudioStreamStats: {
|
if (incomingType == PacketTypeAudioStreamStats) {
|
||||||
if (incomingType != PacketTypeAudioStreamStats) {
|
QMetaObject::invokeMethod(&application->_audio, "parseAudioStreamStatsPacket", Qt::QueuedConnection,
|
||||||
QMetaObject::invokeMethod(&application->_audio, "addReceivedAudioToStream", Qt::QueuedConnection,
|
Q_ARG(QByteArray, incomingPacket));
|
||||||
|
} else if (incomingType == PacketTypeAudioEnvironment) {
|
||||||
|
QMetaObject::invokeMethod(&application->_audio, "parseAudioEnvironmentData", Qt::QueuedConnection,
|
||||||
Q_ARG(QByteArray, incomingPacket));
|
Q_ARG(QByteArray, incomingPacket));
|
||||||
} else {
|
} else {
|
||||||
QMetaObject::invokeMethod(&application->_audio, "parseAudioStreamStatsPacket", Qt::QueuedConnection,
|
QMetaObject::invokeMethod(&application->_audio, "addReceivedAudioToStream", Qt::QueuedConnection,
|
||||||
Q_ARG(QByteArray, incomingPacket));
|
Q_ARG(QByteArray, incomingPacket));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1266,7 +1266,6 @@ void Menu::changeVSync() {
|
||||||
}
|
}
|
||||||
void Menu::changeRenderTargetFramerate(QAction* action) {
|
void Menu::changeRenderTargetFramerate(QAction* action) {
|
||||||
bool vsynOn = Application::getInstance()->isVSyncOn();
|
bool vsynOn = Application::getInstance()->isVSyncOn();
|
||||||
unsigned int framerate = Application::getInstance()->getRenderTargetFramerate();
|
|
||||||
|
|
||||||
QString text = action->text();
|
QString text = action->text();
|
||||||
if (text == MenuOption::RenderTargetFramerateUnlimited) {
|
if (text == MenuOption::RenderTargetFramerateUnlimited) {
|
||||||
|
@ -1315,7 +1314,7 @@ void Menu::displayNameLocationResponse(const QString& errorString) {
|
||||||
void Menu::toggleLocationList() {
|
void Menu::toggleLocationList() {
|
||||||
if (!_userLocationsDialog) {
|
if (!_userLocationsDialog) {
|
||||||
JavascriptObjectMap locationObjectMap;
|
JavascriptObjectMap locationObjectMap;
|
||||||
locationObjectMap.insert("InterfaceLocation", LocationScriptingInterface::getInstance());
|
locationObjectMap.insert("InterfaceLocation", &AddressManager::getInstance());
|
||||||
_userLocationsDialog = DataWebDialog::dialogForPath("/user/locations", locationObjectMap);
|
_userLocationsDialog = DataWebDialog::dialogForPath("/user/locations", locationObjectMap);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1359,7 +1358,7 @@ void Menu::nameLocation() {
|
||||||
|
|
||||||
if (!_newLocationDialog) {
|
if (!_newLocationDialog) {
|
||||||
JavascriptObjectMap locationObjectMap;
|
JavascriptObjectMap locationObjectMap;
|
||||||
locationObjectMap.insert("InterfaceLocation", LocationScriptingInterface::getInstance());
|
locationObjectMap.insert("InterfaceLocation", &AddressManager::getInstance());
|
||||||
_newLocationDialog = DataWebDialog::dialogForPath("/user/locations/new", locationObjectMap);
|
_newLocationDialog = DataWebDialog::dialogForPath("/user/locations/new", locationObjectMap);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -111,6 +111,8 @@ void Batch::runCommand(Command com, uint32 offset) {
|
||||||
CASE_COMMAND(glColor4f);
|
CASE_COMMAND(glColor4f);
|
||||||
CASE_COMMAND(glMaterialf);
|
CASE_COMMAND(glMaterialf);
|
||||||
CASE_COMMAND(glMaterialfv);
|
CASE_COMMAND(glMaterialfv);
|
||||||
|
default:
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1752,7 +1752,8 @@ int Model::renderMeshes(gpu::Batch& batch, RenderMode mode, bool translucent, fl
|
||||||
mesh.texCoords.size() * sizeof(glm::vec2) +
|
mesh.texCoords.size() * sizeof(glm::vec2) +
|
||||||
(mesh.blendshapes.isEmpty() ? vertexCount * 2 * sizeof(glm::vec3) : 0);
|
(mesh.blendshapes.isEmpty() ? vertexCount * 2 * sizeof(glm::vec3) : 0);
|
||||||
//skinProgram->setAttributeBuffer(skinLocations->clusterIndices, GL_FLOAT, offset, 4);
|
//skinProgram->setAttributeBuffer(skinLocations->clusterIndices, GL_FLOAT, offset, 4);
|
||||||
GLBATCH(glVertexAttribPointer)(skinLocations->clusterIndices, 4, GL_FLOAT, GL_TRUE, 0, (const void*) offset);
|
GLBATCH(glVertexAttribPointer)(skinLocations->clusterIndices, 4, GL_FLOAT, GL_TRUE, 0,
|
||||||
|
reinterpret_cast<const void*>(offset));
|
||||||
//skinProgram->setAttributeBuffer(skinLocations->clusterWeights, GL_FLOAT,
|
//skinProgram->setAttributeBuffer(skinLocations->clusterWeights, GL_FLOAT,
|
||||||
// offset + vertexCount * sizeof(glm::vec4), 4);
|
// offset + vertexCount * sizeof(glm::vec4), 4);
|
||||||
GLBATCH(glVertexAttribPointer)(skinLocations->clusterWeights, 4, GL_FLOAT, GL_TRUE, 0, (const void*) (offset + vertexCount * sizeof(glm::vec4)));
|
GLBATCH(glVertexAttribPointer)(skinLocations->clusterWeights, 4, GL_FLOAT, GL_TRUE, 0, (const void*) (offset + vertexCount * sizeof(glm::vec4)));
|
||||||
|
|
|
@ -83,6 +83,12 @@ void InboundAudioStream::clearBuffer() {
|
||||||
_currentJitterBufferFrames = 0;
|
_currentJitterBufferFrames = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void InboundAudioStream::setReverb(float reverbTime, float wetLevel) {
|
||||||
|
_hasReverb = true;
|
||||||
|
_reverbTime = reverbTime;
|
||||||
|
_wetLevel = wetLevel;
|
||||||
|
}
|
||||||
|
|
||||||
void InboundAudioStream::perSecondCallbackForUpdatingStats() {
|
void InboundAudioStream::perSecondCallbackForUpdatingStats() {
|
||||||
_incomingSequenceNumberStats.pushStatsToHistory();
|
_incomingSequenceNumberStats.pushStatsToHistory();
|
||||||
_timeGapStatsForDesiredCalcOnTooManyStarves.currentIntervalComplete();
|
_timeGapStatsForDesiredCalcOnTooManyStarves.currentIntervalComplete();
|
||||||
|
@ -163,22 +169,9 @@ int InboundAudioStream::parseData(const QByteArray& packet) {
|
||||||
}
|
}
|
||||||
|
|
||||||
int InboundAudioStream::parseStreamProperties(PacketType type, const QByteArray& packetAfterSeqNum, int& numAudioSamples) {
|
int InboundAudioStream::parseStreamProperties(PacketType type, const QByteArray& packetAfterSeqNum, int& numAudioSamples) {
|
||||||
int read = 0;
|
|
||||||
if (type == PacketTypeMixedAudio) {
|
|
||||||
memcpy(&_hasReverb, packetAfterSeqNum.data() + read, sizeof(bool));
|
|
||||||
read += sizeof(bool);
|
|
||||||
|
|
||||||
if (_hasReverb) {
|
|
||||||
memcpy(&_reverbTime, packetAfterSeqNum.data() + read, sizeof(float));
|
|
||||||
read += sizeof(float);
|
|
||||||
memcpy(&_wetLevel, packetAfterSeqNum.data() + read, sizeof(float));
|
|
||||||
read += sizeof(float);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// mixed audio packets do not have any info between the seq num and the audio data.
|
// mixed audio packets do not have any info between the seq num and the audio data.
|
||||||
numAudioSamples = (packetAfterSeqNum.size() - read) / sizeof(int16_t);
|
numAudioSamples = packetAfterSeqNum.size() / sizeof(int16_t);
|
||||||
return read;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int InboundAudioStream::parseAudioData(PacketType type, const QByteArray& packetAfterStreamProperties, int numAudioSamples) {
|
int InboundAudioStream::parseAudioData(PacketType type, const QByteArray& packetAfterStreamProperties, int numAudioSamples) {
|
||||||
|
|
|
@ -45,6 +45,9 @@ const int DEFAULT_WINDOW_SECONDS_FOR_DESIRED_CALC_ON_TOO_MANY_STARVES = 50;
|
||||||
const int DEFAULT_WINDOW_SECONDS_FOR_DESIRED_REDUCTION = 10;
|
const int DEFAULT_WINDOW_SECONDS_FOR_DESIRED_REDUCTION = 10;
|
||||||
const bool DEFAULT_REPETITION_WITH_FADE = true;
|
const bool DEFAULT_REPETITION_WITH_FADE = true;
|
||||||
|
|
||||||
|
// Audio Env bitset
|
||||||
|
const int HAS_REVERB_BIT = 0; // 1st bit
|
||||||
|
|
||||||
class InboundAudioStream : public NodeData {
|
class InboundAudioStream : public NodeData {
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
public:
|
public:
|
||||||
|
@ -158,6 +161,8 @@ public:
|
||||||
bool hasReverb() const { return _hasReverb; }
|
bool hasReverb() const { return _hasReverb; }
|
||||||
float getRevebTime() const { return _reverbTime; }
|
float getRevebTime() const { return _reverbTime; }
|
||||||
float getWetLevel() const { return _wetLevel; }
|
float getWetLevel() const { return _wetLevel; }
|
||||||
|
void setReverb(float reverbTime, float wetLevel);
|
||||||
|
void clearReverb() { _hasReverb = false; }
|
||||||
|
|
||||||
public slots:
|
public slots:
|
||||||
/// This function should be called every second for all the stats to function properly. If dynamic jitter buffers
|
/// This function should be called every second for all the stats to function properly. If dynamic jitter buffers
|
||||||
|
|
|
@ -15,6 +15,7 @@
|
||||||
#include <qstringlist.h>
|
#include <qstringlist.h>
|
||||||
|
|
||||||
#include <GLMHelpers.h>
|
#include <GLMHelpers.h>
|
||||||
|
#include <UUID.h>
|
||||||
|
|
||||||
#include "NodeList.h"
|
#include "NodeList.h"
|
||||||
|
|
||||||
|
@ -71,6 +72,11 @@ const QString AddressManager::currentPath(bool withOrientation) const {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QString AddressManager::getDomainID() const {
|
||||||
|
const QUuid& domainID = NodeList::getInstance()->getDomainHandler().getUUID();
|
||||||
|
return domainID.isNull() ? "" : uuidStringWithoutCurlyBraces(domainID);
|
||||||
|
}
|
||||||
|
|
||||||
const JSONCallbackParameters& AddressManager::apiCallbackParameters() {
|
const JSONCallbackParameters& AddressManager::apiCallbackParameters() {
|
||||||
static bool hasSetupParameters = false;
|
static bool hasSetupParameters = false;
|
||||||
static JSONCallbackParameters callbackParams;
|
static JSONCallbackParameters callbackParams;
|
||||||
|
|
|
@ -31,6 +31,7 @@ class AddressManager : public QObject {
|
||||||
Q_PROPERTY(QString protocol READ getProtocol)
|
Q_PROPERTY(QString protocol READ getProtocol)
|
||||||
Q_PROPERTY(QString hostname READ getCurrentDomain)
|
Q_PROPERTY(QString hostname READ getCurrentDomain)
|
||||||
Q_PROPERTY(QString pathname READ currentPath)
|
Q_PROPERTY(QString pathname READ currentPath)
|
||||||
|
Q_PROPERTY(QString domainID READ getDomainID)
|
||||||
public:
|
public:
|
||||||
static AddressManager& getInstance();
|
static AddressManager& getInstance();
|
||||||
|
|
||||||
|
@ -41,6 +42,7 @@ public:
|
||||||
const QString currentPath(bool withOrientation = true) const;
|
const QString currentPath(bool withOrientation = true) const;
|
||||||
|
|
||||||
const QString& getCurrentDomain() const { return _currentDomain; }
|
const QString& getCurrentDomain() const { return _currentDomain; }
|
||||||
|
QString getDomainID() const;
|
||||||
|
|
||||||
void attemptPlaceNameLookup(const QString& lookupString);
|
void attemptPlaceNameLookup(const QString& lookupString);
|
||||||
|
|
||||||
|
|
|
@ -19,10 +19,11 @@
|
||||||
#include <QtCore/QUrl>
|
#include <QtCore/QUrl>
|
||||||
#include <QtNetwork/QHostInfo>
|
#include <QtNetwork/QHostInfo>
|
||||||
|
|
||||||
|
#include <LogHandler.h>
|
||||||
|
|
||||||
#include "AccountManager.h"
|
#include "AccountManager.h"
|
||||||
#include "Assignment.h"
|
#include "Assignment.h"
|
||||||
#include "HifiSockAddr.h"
|
#include "HifiSockAddr.h"
|
||||||
#include "Logging.h"
|
|
||||||
#include "LimitedNodeList.h"
|
#include "LimitedNodeList.h"
|
||||||
#include "PacketHeaders.h"
|
#include "PacketHeaders.h"
|
||||||
#include "SharedUtil.h"
|
#include "SharedUtil.h"
|
||||||
|
@ -211,8 +212,11 @@ bool LimitedNodeList::packetVersionAndHashMatch(const QByteArray& packet) {
|
||||||
<< uuidFromPacketHeader(packet);
|
<< uuidFromPacketHeader(packet);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
static QString repeatedMessage
|
||||||
|
= LogHandler::getInstance().addRepeatedMessageRegex("Packet of type \\d+ received from unknown node with UUID");
|
||||||
|
|
||||||
qDebug() << "Packet of type" << checkType << "received from unknown node with UUID"
|
qDebug() << "Packet of type" << checkType << "received from unknown node with UUID"
|
||||||
<< uuidFromPacketHeader(packet);
|
<< qPrintable(uuidStringWithoutCurlyBraces(uuidFromPacketHeader(packet)));
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
return true;
|
return true;
|
||||||
|
|
|
@ -1,126 +0,0 @@
|
||||||
//
|
|
||||||
// Logging.cpp
|
|
||||||
// libraries/networking/src
|
|
||||||
//
|
|
||||||
// Created by Stephen Birarda on 6/11/13.
|
|
||||||
// Copyright 2013 High Fidelity, Inc.
|
|
||||||
//
|
|
||||||
// Distributed under the Apache License, Version 2.0.
|
|
||||||
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
|
||||||
//
|
|
||||||
|
|
||||||
#include <cstring>
|
|
||||||
#include <cstdio>
|
|
||||||
#include <iostream>
|
|
||||||
#include <ctime>
|
|
||||||
//#include <netdb.h> // not available on windows, apparently not needed on mac
|
|
||||||
|
|
||||||
#ifdef _WIN32
|
|
||||||
#include <process.h>
|
|
||||||
#define getpid _getpid
|
|
||||||
#define getppid _getpid // hack to build
|
|
||||||
#define pid_t int // hack to build
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#include <QtNetwork/QHostInfo>
|
|
||||||
|
|
||||||
#include "HifiSockAddr.h"
|
|
||||||
#include "SharedUtil.h"
|
|
||||||
#include "NodeList.h"
|
|
||||||
|
|
||||||
#include "Logging.h"
|
|
||||||
|
|
||||||
HifiSockAddr Logging::_logstashSocket = HifiSockAddr();
|
|
||||||
QString Logging::_targetName = QString();
|
|
||||||
|
|
||||||
const HifiSockAddr& Logging::socket() {
|
|
||||||
|
|
||||||
if (_logstashSocket.getAddress().isNull()) {
|
|
||||||
// we need to construct the socket object
|
|
||||||
// use the constant port
|
|
||||||
_logstashSocket.setPort(htons(LOGSTASH_UDP_PORT));
|
|
||||||
|
|
||||||
// lookup the IP address for the constant hostname
|
|
||||||
QHostInfo hostInfo = QHostInfo::fromName(LOGSTASH_HOSTNAME);
|
|
||||||
if (!hostInfo.addresses().isEmpty()) {
|
|
||||||
// use the first IP address
|
|
||||||
_logstashSocket.setAddress(hostInfo.addresses().first());
|
|
||||||
} else {
|
|
||||||
qDebug("Failed to lookup logstash IP - will try again on next log attempt.");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return _logstashSocket;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool Logging::shouldSendStats() {
|
|
||||||
static bool shouldSendStats = isInEnvironment("production");
|
|
||||||
return shouldSendStats;
|
|
||||||
}
|
|
||||||
|
|
||||||
void Logging::stashValue(char statType, const char* key, float value) {
|
|
||||||
static char logstashPacket[MAX_PACKET_SIZE];
|
|
||||||
|
|
||||||
// load up the logstash packet with the key and the passed float value
|
|
||||||
// send it to 4 decimal places
|
|
||||||
int numPacketBytes = sprintf(logstashPacket, "%c %s %.4f", statType, key, value);
|
|
||||||
|
|
||||||
NodeList *nodeList = NodeList::getInstance();
|
|
||||||
|
|
||||||
if (nodeList) {
|
|
||||||
nodeList->getNodeSocket().writeDatagram(logstashPacket, numPacketBytes,
|
|
||||||
_logstashSocket.getAddress(), _logstashSocket.getPort());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
const char* stringForLogType(QtMsgType msgType) {
|
|
||||||
switch (msgType) {
|
|
||||||
case QtDebugMsg:
|
|
||||||
return "DEBUG";
|
|
||||||
case QtCriticalMsg:
|
|
||||||
return "CRITICAL";
|
|
||||||
case QtFatalMsg:
|
|
||||||
return "FATAL";
|
|
||||||
case QtWarningMsg:
|
|
||||||
return "WARNING";
|
|
||||||
default:
|
|
||||||
return "UNKNOWN";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// the following will produce 2000-10-02 13:55:36 -0700
|
|
||||||
const char DATE_STRING_FORMAT[] = "%Y-%m-%d %H:%M:%S %z";
|
|
||||||
|
|
||||||
void Logging::verboseMessageHandler(QtMsgType type, const QMessageLogContext& context, const QString& message) {
|
|
||||||
if (message.isEmpty()) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
// log prefix is in the following format
|
|
||||||
// [DEBUG] [TIMESTAMP] [PID:PARENT_PID] [TARGET] logged string
|
|
||||||
|
|
||||||
QString prefixString = QString("[%1]").arg(stringForLogType(type));
|
|
||||||
|
|
||||||
time_t rawTime;
|
|
||||||
time(&rawTime);
|
|
||||||
struct tm* localTime = localtime(&rawTime);
|
|
||||||
|
|
||||||
char dateString[100];
|
|
||||||
strftime(dateString, sizeof(dateString), DATE_STRING_FORMAT, localTime);
|
|
||||||
|
|
||||||
prefixString.append(QString(" [%1]").arg(dateString));
|
|
||||||
|
|
||||||
prefixString.append(QString(" [%1").arg(getpid()));
|
|
||||||
|
|
||||||
pid_t parentProcessID = getppid();
|
|
||||||
if (parentProcessID != 0) {
|
|
||||||
prefixString.append(QString(":%1]").arg(parentProcessID));
|
|
||||||
} else {
|
|
||||||
prefixString.append("]");
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!_targetName.isEmpty()) {
|
|
||||||
prefixString.append(QString(" [%1]").arg(_targetName));
|
|
||||||
}
|
|
||||||
|
|
||||||
fprintf(stdout, "%s %s\n", prefixString.toLocal8Bit().constData(), message.toLocal8Bit().constData());
|
|
||||||
}
|
|
|
@ -1,54 +0,0 @@
|
||||||
//
|
|
||||||
// Logging.h
|
|
||||||
// libraries/networking/src
|
|
||||||
//
|
|
||||||
// Created by Stephen Birarda on 6/11/13.
|
|
||||||
// Copyright 2013 High Fidelity, Inc.
|
|
||||||
//
|
|
||||||
// Distributed under the Apache License, Version 2.0.
|
|
||||||
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
|
||||||
//
|
|
||||||
|
|
||||||
#ifndef hifi_Logging_h
|
|
||||||
#define hifi_Logging_h
|
|
||||||
|
|
||||||
#include <QtCore/QString>
|
|
||||||
|
|
||||||
const int LOGSTASH_UDP_PORT = 9500;
|
|
||||||
const char LOGSTASH_HOSTNAME[] = "graphite.highfidelity.io";
|
|
||||||
|
|
||||||
const char STAT_TYPE_TIMER = 't';
|
|
||||||
const char STAT_TYPE_COUNTER = 'c';
|
|
||||||
const char STAT_TYPE_GAUGE = 'g';
|
|
||||||
|
|
||||||
class HifiSockAddr;
|
|
||||||
|
|
||||||
/// Handles custom message handling and sending of stats/logs to Logstash instance
|
|
||||||
class Logging {
|
|
||||||
public:
|
|
||||||
/// \return the socket used to send stats to logstash
|
|
||||||
static const HifiSockAddr& socket();
|
|
||||||
|
|
||||||
/// checks if this target should send stats to logstash, given its current environment
|
|
||||||
/// \return true if the caller should send stats to logstash
|
|
||||||
static bool shouldSendStats();
|
|
||||||
|
|
||||||
/// stashes a float value to Logstash instance
|
|
||||||
/// \param statType a stat type from the constants in this file
|
|
||||||
/// \param key the key at which to store the stat
|
|
||||||
/// \param value the value to store
|
|
||||||
static void stashValue(char statType, const char* key, float value);
|
|
||||||
|
|
||||||
/// sets the target name to output via the verboseMessageHandler, called once before logging begins
|
|
||||||
/// \param targetName the desired target name to output in logs
|
|
||||||
static void setTargetName(const QString& targetName) { _targetName = targetName; }
|
|
||||||
|
|
||||||
/// a qtMessageHandler that can be hooked up to a target that links to Qt
|
|
||||||
/// prints various process, message type, and time information
|
|
||||||
static void verboseMessageHandler(QtMsgType type, const QMessageLogContext& context, const QString &message);
|
|
||||||
private:
|
|
||||||
static HifiSockAddr _logstashSocket;
|
|
||||||
static QString _targetName;
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // hifi_Logging_h
|
|
|
@ -15,10 +15,11 @@
|
||||||
#include <QtCore/QUrl>
|
#include <QtCore/QUrl>
|
||||||
#include <QtNetwork/QHostInfo>
|
#include <QtNetwork/QHostInfo>
|
||||||
|
|
||||||
|
#include <LogHandler.h>
|
||||||
|
|
||||||
#include "AccountManager.h"
|
#include "AccountManager.h"
|
||||||
#include "Assignment.h"
|
#include "Assignment.h"
|
||||||
#include "HifiSockAddr.h"
|
#include "HifiSockAddr.h"
|
||||||
#include "Logging.h"
|
|
||||||
#include "NodeList.h"
|
#include "NodeList.h"
|
||||||
#include "PacketHeaders.h"
|
#include "PacketHeaders.h"
|
||||||
#include "SharedUtil.h"
|
#include "SharedUtil.h"
|
||||||
|
|
|
@ -53,7 +53,7 @@ PacketVersion versionForPacketType(PacketType type) {
|
||||||
case PacketTypeSilentAudioFrame:
|
case PacketTypeSilentAudioFrame:
|
||||||
return 4;
|
return 4;
|
||||||
case PacketTypeMixedAudio:
|
case PacketTypeMixedAudio:
|
||||||
return 2;
|
return 1;
|
||||||
case PacketTypeAvatarData:
|
case PacketTypeAvatarData:
|
||||||
return 3;
|
return 3;
|
||||||
case PacketTypeAvatarIdentity:
|
case PacketTypeAvatarIdentity:
|
||||||
|
@ -71,11 +71,9 @@ PacketVersion versionForPacketType(PacketType type) {
|
||||||
return 1;
|
return 1;
|
||||||
case PacketTypeOctreeStats:
|
case PacketTypeOctreeStats:
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
case PacketTypeEntityAddOrEdit:
|
case PacketTypeEntityAddOrEdit:
|
||||||
case PacketTypeEntityData:
|
case PacketTypeEntityData:
|
||||||
return VERSION_ENTITIES_SUPPORT_DIMENSIONS;
|
return VERSION_ENTITIES_SUPPORT_DIMENSIONS;
|
||||||
|
|
||||||
case PacketTypeEntityErase:
|
case PacketTypeEntityErase:
|
||||||
return 2;
|
return 2;
|
||||||
case PacketTypeAudioStreamStats:
|
case PacketTypeAudioStreamStats:
|
||||||
|
@ -135,8 +133,13 @@ QString nameForPacketType(PacketType type) {
|
||||||
PACKET_TYPE_NAME_LOOKUP(PacketTypeEntityAddResponse);
|
PACKET_TYPE_NAME_LOOKUP(PacketTypeEntityAddResponse);
|
||||||
PACKET_TYPE_NAME_LOOKUP(PacketTypeOctreeDataNack);
|
PACKET_TYPE_NAME_LOOKUP(PacketTypeOctreeDataNack);
|
||||||
PACKET_TYPE_NAME_LOOKUP(PacketTypeVoxelEditNack);
|
PACKET_TYPE_NAME_LOOKUP(PacketTypeVoxelEditNack);
|
||||||
|
PACKET_TYPE_NAME_LOOKUP(PacketTypeAudioEnvironment);
|
||||||
PACKET_TYPE_NAME_LOOKUP(PacketTypeEntityEditNack);
|
PACKET_TYPE_NAME_LOOKUP(PacketTypeEntityEditNack);
|
||||||
PACKET_TYPE_NAME_LOOKUP(PacketTypeSignedTransactionPayment);
|
PACKET_TYPE_NAME_LOOKUP(PacketTypeSignedTransactionPayment);
|
||||||
|
PACKET_TYPE_NAME_LOOKUP(PacketTypeIceServerHeartbeat);
|
||||||
|
PACKET_TYPE_NAME_LOOKUP(PacketTypeIceServerHeartbeatResponse);
|
||||||
|
PACKET_TYPE_NAME_LOOKUP(PacketTypeUnverifiedPing);
|
||||||
|
PACKET_TYPE_NAME_LOOKUP(PacketTypeUnverifiedPingReply);
|
||||||
default:
|
default:
|
||||||
return QString("Type: ") + QString::number((int)type);
|
return QString("Type: ") + QString::number((int)type);
|
||||||
}
|
}
|
||||||
|
|
|
@ -68,7 +68,7 @@ enum PacketType {
|
||||||
PacketTypeEntityAddResponse,
|
PacketTypeEntityAddResponse,
|
||||||
PacketTypeOctreeDataNack, // 45
|
PacketTypeOctreeDataNack, // 45
|
||||||
PacketTypeVoxelEditNack,
|
PacketTypeVoxelEditNack,
|
||||||
UNUSED_6,
|
PacketTypeAudioEnvironment,
|
||||||
PacketTypeEntityEditNack, // 48
|
PacketTypeEntityEditNack, // 48
|
||||||
PacketTypeSignedTransactionPayment,
|
PacketTypeSignedTransactionPayment,
|
||||||
PacketTypeIceServerHeartbeat,
|
PacketTypeIceServerHeartbeat,
|
||||||
|
|
|
@ -14,7 +14,8 @@
|
||||||
#include <QtCore/QThread>
|
#include <QtCore/QThread>
|
||||||
#include <QtCore/QTimer>
|
#include <QtCore/QTimer>
|
||||||
|
|
||||||
#include "Logging.h"
|
#include <LogHandler.h>
|
||||||
|
|
||||||
#include "ThreadedAssignment.h"
|
#include "ThreadedAssignment.h"
|
||||||
|
|
||||||
ThreadedAssignment::ThreadedAssignment(const QByteArray& packet) :
|
ThreadedAssignment::ThreadedAssignment(const QByteArray& packet) :
|
||||||
|
@ -54,7 +55,7 @@ void ThreadedAssignment::setFinished(bool isFinished) {
|
||||||
|
|
||||||
void ThreadedAssignment::commonInit(const QString& targetName, NodeType_t nodeType, bool shouldSendStats) {
|
void ThreadedAssignment::commonInit(const QString& targetName, NodeType_t nodeType, bool shouldSendStats) {
|
||||||
// change the logging target name while the assignment is running
|
// change the logging target name while the assignment is running
|
||||||
Logging::setTargetName(targetName);
|
LogHandler::getInstance().setTargetName(targetName);
|
||||||
|
|
||||||
NodeList* nodeList = NodeList::getInstance();
|
NodeList* nodeList = NodeList::getInstance();
|
||||||
nodeList->setOwnerType(nodeType);
|
nodeList->setOwnerType(nodeType);
|
||||||
|
|
144
libraries/shared/src/LogHandler.cpp
Normal file
144
libraries/shared/src/LogHandler.cpp
Normal file
|
@ -0,0 +1,144 @@
|
||||||
|
//
|
||||||
|
// LogHandler.cpp
|
||||||
|
// libraries/shared/src
|
||||||
|
//
|
||||||
|
// Created by Stephen Birarda on 2014-10-28.
|
||||||
|
// Migrated from Logging.cpp created on 6/11/13
|
||||||
|
// Copyright 2014 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#include <time.h>
|
||||||
|
|
||||||
|
#ifdef _WIN32
|
||||||
|
#include <process.h>
|
||||||
|
#define getpid _getpid
|
||||||
|
#define getppid _getpid // hack to build
|
||||||
|
#define pid_t int // hack to build
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#include <qdebug.h>
|
||||||
|
#include <qtimer.h>
|
||||||
|
|
||||||
|
#include "LogHandler.h"
|
||||||
|
|
||||||
|
LogHandler& LogHandler::getInstance() {
|
||||||
|
static LogHandler staticInstance;
|
||||||
|
return staticInstance;
|
||||||
|
}
|
||||||
|
|
||||||
|
LogHandler::LogHandler() :
|
||||||
|
_shouldOutputPID(false)
|
||||||
|
{
|
||||||
|
// setup our timer to flush the verbose logs every 5 seconds
|
||||||
|
QTimer* logFlushTimer = new QTimer(this);
|
||||||
|
connect(logFlushTimer, &QTimer::timeout, this, &LogHandler::flushRepeatedMessages);
|
||||||
|
logFlushTimer->start(VERBOSE_LOG_INTERVAL_SECONDS * 1000);
|
||||||
|
}
|
||||||
|
|
||||||
|
const char* stringForLogType(LogMsgType msgType) {
|
||||||
|
switch (msgType) {
|
||||||
|
case QtDebugMsg:
|
||||||
|
return "DEBUG";
|
||||||
|
case QtCriticalMsg:
|
||||||
|
return "CRITICAL";
|
||||||
|
case QtFatalMsg:
|
||||||
|
return "FATAL";
|
||||||
|
case QtWarningMsg:
|
||||||
|
return "WARNING";
|
||||||
|
case LogSuppressed:
|
||||||
|
return "SUPPRESS";
|
||||||
|
default:
|
||||||
|
return "UNKNOWN";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// the following will produce 2000-10-02 13:55:36 -0700
|
||||||
|
const char DATE_STRING_FORMAT[] = "%Y-%m-%d %H:%M:%S %z";
|
||||||
|
|
||||||
|
void LogHandler::flushRepeatedMessages() {
|
||||||
|
QHash<QString, int>::iterator message = _repeatMessageCountHash.begin();
|
||||||
|
while (message != _repeatMessageCountHash.end()) {
|
||||||
|
|
||||||
|
if (message.value() > 0) {
|
||||||
|
QString repeatMessage = QString("%1 repeated log entries matching \"%2\" - Last entry: \"%3\"")
|
||||||
|
.arg(message.value()).arg(message.key()).arg(_lastRepeatedMessage.value(message.key()));
|
||||||
|
|
||||||
|
QMessageLogContext emptyContext;
|
||||||
|
printMessage(LogSuppressed, emptyContext, repeatMessage);
|
||||||
|
}
|
||||||
|
|
||||||
|
_lastRepeatedMessage.remove(message.key());
|
||||||
|
message = _repeatMessageCountHash.erase(message);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
QString LogHandler::printMessage(LogMsgType type, const QMessageLogContext& context, const QString& message) {
|
||||||
|
|
||||||
|
if (message.isEmpty()) {
|
||||||
|
return QString();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (type == LogDebug) {
|
||||||
|
// for debug messages, check if this matches any of our regexes for repeated log messages
|
||||||
|
foreach(const QString& regexString, getInstance()._repeatedMessageRegexes) {
|
||||||
|
QRegExp repeatRegex(regexString);
|
||||||
|
if (repeatRegex.indexIn(message) != -1) {
|
||||||
|
|
||||||
|
if (!_repeatMessageCountHash.contains(regexString)) {
|
||||||
|
// we have a match but didn't have this yet - output the first one
|
||||||
|
_repeatMessageCountHash[regexString] = 0;
|
||||||
|
|
||||||
|
// break the foreach so we output the first match
|
||||||
|
break;
|
||||||
|
} else {
|
||||||
|
// we have a match - add 1 to the count of repeats for this message and set this as the last repeated message
|
||||||
|
_repeatMessageCountHash[regexString] += 1;
|
||||||
|
_lastRepeatedMessage[regexString] = message;
|
||||||
|
|
||||||
|
// return out, we're not printing this one
|
||||||
|
return QString();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// log prefix is in the following format
|
||||||
|
// [DEBUG] [TIMESTAMP] [PID:PARENT_PID] [TARGET] logged string
|
||||||
|
|
||||||
|
QString prefixString = QString("[%1]").arg(stringForLogType(type));
|
||||||
|
|
||||||
|
time_t rawTime;
|
||||||
|
time(&rawTime);
|
||||||
|
struct tm* localTime = localtime(&rawTime);
|
||||||
|
|
||||||
|
char dateString[100];
|
||||||
|
strftime(dateString, sizeof(dateString), DATE_STRING_FORMAT, localTime);
|
||||||
|
|
||||||
|
prefixString.append(QString(" [%1]").arg(dateString));
|
||||||
|
|
||||||
|
if (_shouldOutputPID) {
|
||||||
|
prefixString.append(QString(" [%1").arg(getpid()));
|
||||||
|
|
||||||
|
pid_t parentProcessID = getppid();
|
||||||
|
if (parentProcessID != 0) {
|
||||||
|
prefixString.append(QString(":%1]").arg(parentProcessID));
|
||||||
|
} else {
|
||||||
|
prefixString.append("]");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!_targetName.isEmpty()) {
|
||||||
|
prefixString.append(QString(" [%1]").arg(_targetName));
|
||||||
|
}
|
||||||
|
|
||||||
|
QString logMessage = QString("%1 %2").arg(prefixString, message);
|
||||||
|
fprintf(stdout, "%s\n", qPrintable(logMessage));
|
||||||
|
return logMessage;
|
||||||
|
}
|
||||||
|
|
||||||
|
void LogHandler::verboseMessageHandler(QtMsgType type, const QMessageLogContext& context, const QString& message) {
|
||||||
|
getInstance().printMessage((LogMsgType) type, context, message);
|
||||||
|
}
|
63
libraries/shared/src/LogHandler.h
Normal file
63
libraries/shared/src/LogHandler.h
Normal file
|
@ -0,0 +1,63 @@
|
||||||
|
//
|
||||||
|
// LogHandler.cpp
|
||||||
|
// libraries/shared/src
|
||||||
|
//
|
||||||
|
// Created by Stephen Birarda on 2014-10-28.
|
||||||
|
// Migrated from Logging.cpp created on 6/11/13
|
||||||
|
// Copyright 2014 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#ifndef hifi_LogHandler_h
|
||||||
|
#define hifi_LogHandler_h
|
||||||
|
|
||||||
|
#include <qhash.h>
|
||||||
|
#include <qobject.h>
|
||||||
|
#include <qregexp.h>
|
||||||
|
#include <qset.h>
|
||||||
|
#include <qstring.h>
|
||||||
|
|
||||||
|
const int VERBOSE_LOG_INTERVAL_SECONDS = 5;
|
||||||
|
|
||||||
|
enum LogMsgType {
|
||||||
|
LogDebug,
|
||||||
|
LogWarning,
|
||||||
|
LogCritical,
|
||||||
|
LogFatal,
|
||||||
|
LogSuppressed
|
||||||
|
};
|
||||||
|
|
||||||
|
/// Handles custom message handling and sending of stats/logs to Logstash instance
|
||||||
|
class LogHandler : public QObject {
|
||||||
|
Q_OBJECT
|
||||||
|
public:
|
||||||
|
static LogHandler& getInstance();
|
||||||
|
|
||||||
|
/// sets the target name to output via the verboseMessageHandler, called once before logging begins
|
||||||
|
/// \param targetName the desired target name to output in logs
|
||||||
|
void setTargetName(const QString& targetName) { _targetName = targetName; }
|
||||||
|
|
||||||
|
void setShouldOutputPID(bool shouldOutputPID) { _shouldOutputPID = shouldOutputPID; }
|
||||||
|
|
||||||
|
QString printMessage(LogMsgType type, const QMessageLogContext& context, const QString &message);
|
||||||
|
|
||||||
|
/// a qtMessageHandler that can be hooked up to a target that links to Qt
|
||||||
|
/// prints various process, message type, and time information
|
||||||
|
static void verboseMessageHandler(QtMsgType type, const QMessageLogContext& context, const QString &message);
|
||||||
|
|
||||||
|
const QString& addRepeatedMessageRegex(const QString& regexString) { return *_repeatedMessageRegexes.insert(regexString); }
|
||||||
|
private:
|
||||||
|
LogHandler();
|
||||||
|
|
||||||
|
void flushRepeatedMessages();
|
||||||
|
|
||||||
|
QString _targetName;
|
||||||
|
bool _shouldOutputPID;
|
||||||
|
QSet<QString> _repeatedMessageRegexes;
|
||||||
|
QHash<QString, int> _repeatMessageCountHash;
|
||||||
|
QHash<QString, QString> _lastRepeatedMessage;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // hifi_LogHandler_h
|
Loading…
Reference in a new issue