From 4103cc1cde0d710021fed890cd61288f608a4e03 Mon Sep 17 00:00:00 2001 From: Stephen Birarda Date: Tue, 28 Jan 2014 10:36:08 -0800 Subject: [PATCH 01/16] packet header changes and beginning of conversion to QByteArray --- animation-server/src/AnimationServer.cpp | 42 ++- assignment-client/src/Agent.cpp | 18 +- assignment-client/src/Agent.h | 2 +- assignment-client/src/AssignmentClient.cpp | 71 ++--- assignment-client/src/AssignmentFactory.cpp | 18 +- assignment-client/src/AssignmentFactory.h | 2 +- assignment-client/src/audio/AudioMixer.cpp | 24 +- assignment-client/src/audio/AudioMixer.h | 2 +- .../src/audio/AudioMixerClientData.cpp | 15 +- .../src/audio/AudioMixerClientData.h | 2 +- .../src/audio/AvatarAudioRingBuffer.cpp | 6 +- .../src/audio/AvatarAudioRingBuffer.h | 2 +- assignment-client/src/avatars/AvatarMixer.cpp | 82 ++--- assignment-client/src/avatars/AvatarMixer.h | 2 +- .../src/metavoxels/MetavoxelServer.cpp | 8 +- .../src/metavoxels/MetavoxelServer.h | 2 +- data-server/src/DataServer.cpp | 118 +++----- domain-server/src/DomainServer.cpp | 186 +++++------- domain-server/src/DomainServer.h | 2 - interface/src/Application.cpp | 61 ++-- interface/src/Application.h | 10 +- interface/src/Audio.cpp | 19 +- interface/src/DatagramProcessor.cpp | 86 +++--- interface/src/Environment.cpp | 18 +- interface/src/Environment.h | 2 +- interface/src/MetavoxelSystem.cpp | 3 +- interface/src/ParticleTreeRenderer.h | 4 +- interface/src/VoxelPacketProcessor.cpp | 45 +-- interface/src/VoxelPacketProcessor.h | 2 +- interface/src/VoxelSystem.cpp | 27 +- interface/src/VoxelSystem.h | 2 +- interface/src/avatar/Avatar.cpp | 5 +- interface/src/avatar/Avatar.h | 2 +- interface/src/avatar/AvatarManager.cpp | 19 +- interface/src/avatar/MyAvatar.cpp | 15 +- interface/src/devices/Transmitter.cpp | 2 +- libraries/audio/src/AudioInjector.cpp | 49 ++- libraries/audio/src/AudioRingBuffer.cpp | 6 +- libraries/audio/src/AudioRingBuffer.h | 2 +- .../audio/src/InjectedAudioRingBuffer.cpp | 26 +- libraries/audio/src/InjectedAudioRingBuffer.h | 2 +- .../audio/src/PositionalAudioRingBuffer.cpp | 31 +- .../audio/src/PositionalAudioRingBuffer.h | 6 +- libraries/avatars/src/AvatarData.cpp | 130 ++++---- libraries/avatars/src/AvatarData.h | 4 +- libraries/avatars/src/HandData.cpp | 43 ++- libraries/avatars/src/HandData.h | 2 +- libraries/metavoxels/src/MetavoxelUtil.cpp | 2 +- .../src/OctreeInboundPacketProcessor.cpp | 31 +- .../src/OctreeInboundPacketProcessor.h | 2 +- .../octree-server/src/OctreeQueryNode.cpp | 2 +- libraries/octree-server/src/OctreeQueryNode.h | 2 +- .../octree-server/src/OctreeSendThread.cpp | 2 +- libraries/octree-server/src/OctreeServer.cpp | 36 +-- libraries/octree-server/src/OctreeServer.h | 4 +- libraries/octree/src/JurisdictionListener.cpp | 10 +- libraries/octree/src/JurisdictionListener.h | 8 +- libraries/octree/src/JurisdictionMap.cpp | 10 +- libraries/octree/src/JurisdictionMap.h | 4 +- libraries/octree/src/JurisdictionSender.cpp | 12 +- libraries/octree/src/JurisdictionSender.h | 4 +- libraries/octree/src/Octree.cpp | 19 +- libraries/octree/src/Octree.h | 8 +- .../octree/src/OctreeEditPacketSender.cpp | 22 +- libraries/octree/src/OctreeEditPacketSender.h | 12 +- libraries/octree/src/OctreePacketData.h | 6 +- libraries/octree/src/OctreeQuery.cpp | 8 +- libraries/octree/src/OctreeQuery.h | 2 +- libraries/octree/src/OctreeRenderer.cpp | 8 +- libraries/octree/src/OctreeRenderer.h | 6 +- libraries/octree/src/OctreeSceneStats.cpp | 18 +- libraries/octree/src/OctreeSceneStats.h | 5 +- .../particle-server/src/ParticleNodeData.h | 2 +- .../particle-server/src/ParticleServer.cpp | 6 +- .../particle-server/src/ParticleServer.h | 4 +- libraries/particles/src/Particle.cpp | 14 +- libraries/particles/src/Particle.h | 8 +- .../particles/src/ParticleCollisionSystem.cpp | 6 +- .../src/ParticleEditPacketSender.cpp | 4 +- .../particles/src/ParticleEditPacketSender.h | 4 +- libraries/particles/src/ParticleTree.cpp | 38 +-- libraries/particles/src/ParticleTree.h | 8 +- .../src/ParticlesScriptingInterface.cpp | 12 +- .../src/ParticlesScriptingInterface.h | 2 +- libraries/script-engine/src/ScriptEngine.cpp | 16 +- libraries/shared/src/Assignment.cpp | 129 ++------ libraries/shared/src/Assignment.h | 29 +- libraries/shared/src/DataServerClient.cpp | 106 ++----- libraries/shared/src/DataServerClient.h | 8 +- libraries/shared/src/HifiSockAddr.cpp | 32 +- libraries/shared/src/HifiSockAddr.h | 4 +- libraries/shared/src/NetworkPacket.cpp | 31 +- libraries/shared/src/NetworkPacket.h | 15 +- libraries/shared/src/Node.cpp | 19 +- libraries/shared/src/Node.h | 17 +- libraries/shared/src/NodeData.h | 2 +- libraries/shared/src/NodeList.cpp | 285 ++++++++---------- libraries/shared/src/NodeList.h | 18 +- libraries/shared/src/NodeTypes.h | 31 -- libraries/shared/src/PacketHeaders.cpp | 164 +++++----- libraries/shared/src/PacketHeaders.h | 104 ++++--- libraries/shared/src/PacketSender.cpp | 14 +- libraries/shared/src/PacketSender.h | 2 +- .../shared/src/ReceivedPacketProcessor.cpp | 8 +- .../shared/src/ReceivedPacketProcessor.h | 4 +- libraries/shared/src/SharedUtil.cpp | 111 +------ libraries/shared/src/SharedUtil.h | 23 +- libraries/shared/src/ThreadedAssignment.cpp | 4 +- libraries/shared/src/ThreadedAssignment.h | 2 +- libraries/voxel-server/src/VoxelNodeData.h | 2 +- libraries/voxel-server/src/VoxelServer.cpp | 4 +- libraries/voxel-server/src/VoxelServer.h | 4 +- libraries/voxels/src/EnvironmentData.cpp | 4 +- libraries/voxels/src/EnvironmentData.h | 2 +- .../voxels/src/VoxelEditPacketSender.cpp | 103 ++++++- libraries/voxels/src/VoxelEditPacketSender.h | 6 +- libraries/voxels/src/VoxelPacketData.h | 6 +- libraries/voxels/src/VoxelTree.cpp | 38 +-- libraries/voxels/src/VoxelTree.h | 8 +- .../voxels/src/VoxelsScriptingInterface.cpp | 8 +- .../voxels/src/VoxelsScriptingInterface.h | 2 +- 121 files changed, 1331 insertions(+), 1612 deletions(-) delete mode 100644 libraries/shared/src/NodeTypes.h diff --git a/animation-server/src/AnimationServer.cpp b/animation-server/src/AnimationServer.cpp index 6d493b62e5..c436fd1d4b 100644 --- a/animation-server/src/AnimationServer.cpp +++ b/animation-server/src/AnimationServer.cpp @@ -16,7 +16,6 @@ #include #include -#include #include #include #include @@ -152,7 +151,7 @@ static void renderMovingBug() { } // send the "erase message" first... - PACKET_TYPE message = PACKET_TYPE_VOXEL_ERASE; + PacketType message = PacketTypeVoxelErase; ::voxelEditPacketSender->queueVoxelEditMessages(message, VOXELS_PER_BUG, (VoxelDetail*)&details); // Move the bug... @@ -212,7 +211,7 @@ static void renderMovingBug() { } // send the "create message" ... - message = PACKET_TYPE_VOXEL_SET_DESTRUCTIVE; + message = PacketTypeVoxelSetDestructive; ::voxelEditPacketSender->queueVoxelEditMessages(message, VOXELS_PER_BUG, (VoxelDetail*)&details); } @@ -247,7 +246,7 @@ static void sendVoxelBlinkMessage() { detail.green = 0 * ::intensity; detail.blue = 0 * ::intensity; - PACKET_TYPE message = PACKET_TYPE_VOXEL_SET_DESTRUCTIVE; + PacketType message = PacketTypeVoxelSetDestructive; ::voxelEditPacketSender->sendVoxelEditMessage(message, detail); } @@ -264,7 +263,7 @@ unsigned char onColor[3] = { 0, 255, 255 }; const float STRING_OF_LIGHTS_SIZE = 0.125f / TREE_SCALE; // approximately 1/8th meter static void sendBlinkingStringOfLights() { - PACKET_TYPE message = PACKET_TYPE_VOXEL_SET_DESTRUCTIVE; // we're a bully! + PacketType message = PacketTypeVoxelSetDestructive; // we're a bully! float lightScale = STRING_OF_LIGHTS_SIZE; static VoxelDetail details[LIGHTS_PER_SEGMENT]; @@ -370,7 +369,7 @@ const int PACKETS_PER_DANCE_FLOOR = DANCE_FLOOR_VOXELS_PER_PACKET / (DANCE_FLOOR int danceFloorColors[DANCE_FLOOR_WIDTH][DANCE_FLOOR_LENGTH]; void sendDanceFloor() { - PACKET_TYPE message = PACKET_TYPE_VOXEL_SET_DESTRUCTIVE; // we're a bully! + PacketType message = PacketTypeVoxelSetDestructive; // we're a bully! float lightScale = DANCE_FLOOR_LIGHT_SIZE; static VoxelDetail details[DANCE_FLOOR_VOXELS_PER_PACKET]; @@ -486,7 +485,7 @@ bool billboardMessage[BILLBOARD_HEIGHT][BILLBOARD_WIDTH] = { }; static void sendBillboard() { - PACKET_TYPE message = PACKET_TYPE_VOXEL_SET_DESTRUCTIVE; // we're a bully! + PacketType message = PacketTypeVoxelSetDestructive; // we're a bully! float lightScale = BILLBOARD_LIGHT_SIZE; static VoxelDetail details[VOXELS_PER_PACKET]; @@ -557,7 +556,7 @@ void doBuildStreet() { return; } - PACKET_TYPE message = PACKET_TYPE_VOXEL_SET_DESTRUCTIVE; // we're a bully! + PacketType message = PacketTypeVoxelSetDestructive; // we're a bully! static VoxelDetail details[BRICKS_PER_PACKET]; for (int z = 0; z < ROAD_LENGTH; z++) { @@ -823,25 +822,24 @@ AnimationServer::AnimationServer(int &argc, char **argv) : void AnimationServer::readPendingDatagrams() { NodeList* nodeList = NodeList::getInstance(); - static int receivedBytes = 0; - static unsigned char packetData[MAX_PACKET_SIZE]; + static QByteArray receivedPacket; static HifiSockAddr nodeSockAddr; // Nodes sending messages to us... - while (nodeList->getNodeSocket().hasPendingDatagrams() - && (receivedBytes = nodeList->getNodeSocket().readDatagram((char*) packetData, MAX_PACKET_SIZE, - nodeSockAddr.getAddressPointer(), - nodeSockAddr.getPortPointer())) && - packetVersionMatch(packetData, nodeSockAddr)) { - - if (packetData[0] == PACKET_TYPE_JURISDICTION) { - int headerBytes = numBytesForPacketHeader(packetData); - // PACKET_TYPE_JURISDICTION, first byte is the node type... - if (packetData[headerBytes] == NODE_TYPE_VOXEL_SERVER && ::jurisdictionListener) { - ::jurisdictionListener->queueReceivedPacket(nodeSockAddr, packetData, receivedBytes); + while (nodeList->getNodeSocket().hasPendingDatagrams()) { + receivedPacket.resize(nodeList->getNodeSocket().pendingDatagramSize()); + nodeList->getNodeSocket().readDatagram(receivedPacket.data(), receivedPacket.size(), + nodeSockAddr.getAddressPointer(), nodeSockAddr.getPortPointer()); + if (packetVersionMatch(receivedPacket)) { + if (packetTypeForPacket(receivedPacket) == PacketTypeJurisdiction) { + int headerBytes = numBytesForPacketHeader(receivedPacket); + // PacketType_JURISDICTION, first byte is the node type... + if (receivedPacket.data()[headerBytes] == NODE_TYPE_VOXEL_SERVER && ::jurisdictionListener) { + ::jurisdictionListener->queueReceivedPacket(nodeSockAddr, receivedPacket); + } } + NodeList::getInstance()->processNodeData(nodeSockAddr, receivedPacket); } - NodeList::getInstance()->processNodeData(nodeSockAddr, packetData, receivedBytes); } } diff --git a/assignment-client/src/Agent.cpp b/assignment-client/src/Agent.cpp index 4f81c42046..38985a916e 100644 --- a/assignment-client/src/Agent.cpp +++ b/assignment-client/src/Agent.cpp @@ -22,29 +22,27 @@ #include "Agent.h" -Agent::Agent(const unsigned char* dataBuffer, int numBytes) : - ThreadedAssignment(dataBuffer, numBytes) +Agent::Agent(const QByteArray& packet) : + ThreadedAssignment(packet) { } void Agent::processDatagram(const QByteArray& dataByteArray, const HifiSockAddr& senderSockAddr) { - if (dataByteArray[0] == PACKET_TYPE_JURISDICTION) { - int headerBytes = numBytesForPacketHeader((const unsigned char*) dataByteArray.constData()); - // PACKET_TYPE_JURISDICTION, first byte is the node type... + if (packetTypeForPacket(dataByteArray) == PacketTypeJurisdiction) { + int headerBytes = numBytesForPacketHeader(dataByteArray); + // PacketType_JURISDICTION, first byte is the node type... switch (dataByteArray[headerBytes]) { case NODE_TYPE_VOXEL_SERVER: _scriptEngine.getVoxelsScriptingInterface()->getJurisdictionListener()->queueReceivedPacket(senderSockAddr, - (unsigned char*) dataByteArray.data(), - dataByteArray.size()); + dataByteArray); break; case NODE_TYPE_PARTICLE_SERVER: _scriptEngine.getParticlesScriptingInterface()->getJurisdictionListener()->queueReceivedPacket(senderSockAddr, - (unsigned char*) dataByteArray.data(), - dataByteArray.size()); + dataByteArray); break; } } else { - NodeList::getInstance()->processNodeData(senderSockAddr, (unsigned char*) dataByteArray.data(), dataByteArray.size()); + NodeList::getInstance()->processNodeData(senderSockAddr, dataByteArray); } } diff --git a/assignment-client/src/Agent.h b/assignment-client/src/Agent.h index 980885fcf3..bc026084c1 100644 --- a/assignment-client/src/Agent.h +++ b/assignment-client/src/Agent.h @@ -21,7 +21,7 @@ class Agent : public ThreadedAssignment { Q_OBJECT public: - Agent(const unsigned char* dataBuffer, int numBytes); + Agent(const QByteArray& packet); public slots: void run(); diff --git a/assignment-client/src/AssignmentClient.cpp b/assignment-client/src/AssignmentClient.cpp index fc8d2deffd..998ff46217 100644 --- a/assignment-client/src/AssignmentClient.cpp +++ b/assignment-client/src/AssignmentClient.cpp @@ -102,63 +102,58 @@ void AssignmentClient::sendAssignmentRequest() { void AssignmentClient::readPendingDatagrams() { NodeList* nodeList = NodeList::getInstance(); - static unsigned char packetData[1500]; - static qint64 receivedBytes = 0; - static HifiSockAddr senderSockAddr; + QByteArray receivedPacket; + HifiSockAddr senderSockAddr; while (nodeList->getNodeSocket().hasPendingDatagrams()) { + receivedPacket.resize(nodeList->getNodeSocket().pendingDatagramSize()); + nodeList->getNodeSocket().readDatagram(receivedPacket.data(), receivedPacket.size(), + senderSockAddr.getAddressPointer(), senderSockAddr.getPortPointer()); - if ((receivedBytes = nodeList->getNodeSocket().readDatagram((char*) packetData, MAX_PACKET_SIZE, - senderSockAddr.getAddressPointer(), - senderSockAddr.getPortPointer())) - && packetVersionMatch(packetData, senderSockAddr)) { - + if (packetVersionMatch(receivedPacket)) { if (_currentAssignment) { // have the threaded current assignment handle this datagram QMetaObject::invokeMethod(_currentAssignment, "processDatagram", Qt::QueuedConnection, - Q_ARG(QByteArray, QByteArray((char*) packetData, receivedBytes)), + Q_ARG(QByteArray, receivedPacket), Q_ARG(HifiSockAddr, senderSockAddr)); - } else if (packetData[0] == PACKET_TYPE_DEPLOY_ASSIGNMENT || packetData[0] == PACKET_TYPE_CREATE_ASSIGNMENT) { + } else if (packetTypeForPacket(receivedPacket) == PacketTypeCreateAssignment) { if (_currentAssignment) { qDebug() << "Dropping received assignment since we are currently running one."; } else { // construct the deployed assignment from the packet data - _currentAssignment = AssignmentFactory::unpackAssignment(packetData, receivedBytes); + _currentAssignment = AssignmentFactory::unpackAssignment(receivedPacket); qDebug() << "Received an assignment -" << *_currentAssignment; // switch our nodelist domain IP and port to whoever sent us the assignment - if (packetData[0] == PACKET_TYPE_CREATE_ASSIGNMENT) { - nodeList->setDomainSockAddr(senderSockAddr); - nodeList->setOwnerUUID(_currentAssignment->getUUID()); - - qDebug() << "Destination IP for assignment is" << nodeList->getDomainIP().toString(); - - // start the deployed assignment - QThread* workerThread = new QThread(this); - - connect(workerThread, SIGNAL(started()), _currentAssignment, SLOT(run())); - - connect(_currentAssignment, SIGNAL(finished()), this, SLOT(assignmentCompleted())); - connect(_currentAssignment, SIGNAL(finished()), workerThread, SLOT(quit())); - connect(_currentAssignment, SIGNAL(finished()), _currentAssignment, SLOT(deleteLater())); - connect(workerThread, SIGNAL(finished()), workerThread, SLOT(deleteLater())); - - _currentAssignment->moveToThread(workerThread); - - // move the NodeList to the thread used for the _current assignment - nodeList->moveToThread(workerThread); - - // Starts an event loop, and emits workerThread->started() - workerThread->start(); - } else { - qDebug("Received a bad destination socket for assignment."); - } + + nodeList->setDomainSockAddr(senderSockAddr); + nodeList->setOwnerUUID(_currentAssignment->getUUID()); + + qDebug() << "Destination IP for assignment is" << nodeList->getDomainIP().toString(); + + // start the deployed assignment + QThread* workerThread = new QThread(this); + + connect(workerThread, SIGNAL(started()), _currentAssignment, SLOT(run())); + + connect(_currentAssignment, SIGNAL(finished()), this, SLOT(assignmentCompleted())); + connect(_currentAssignment, SIGNAL(finished()), workerThread, SLOT(quit())); + connect(_currentAssignment, SIGNAL(finished()), _currentAssignment, SLOT(deleteLater())); + connect(workerThread, SIGNAL(finished()), workerThread, SLOT(deleteLater())); + + _currentAssignment->moveToThread(workerThread); + + // move the NodeList to the thread used for the _current assignment + nodeList->moveToThread(workerThread); + + // Starts an event loop, and emits workerThread->started() + workerThread->start(); } } else { // have the NodeList attempt to handle it - nodeList->processNodeData(senderSockAddr, packetData, receivedBytes); + nodeList->processNodeData(senderSockAddr, receivedPacket); } } } diff --git a/assignment-client/src/AssignmentFactory.cpp b/assignment-client/src/AssignmentFactory.cpp index b32a909bfe..0b8e089c01 100644 --- a/assignment-client/src/AssignmentFactory.cpp +++ b/assignment-client/src/AssignmentFactory.cpp @@ -18,25 +18,25 @@ #include "avatars/AvatarMixer.h" #include "metavoxels/MetavoxelServer.h" -ThreadedAssignment* AssignmentFactory::unpackAssignment(const unsigned char* dataBuffer, int numBytes) { - int headerBytes = numBytesForPacketHeader(dataBuffer); +ThreadedAssignment* AssignmentFactory::unpackAssignment(const QByteArray& packet) { + int headerBytes = numBytesForPacketHeader(packet); Assignment::Type assignmentType = Assignment::AllTypes; - memcpy(&assignmentType, dataBuffer + headerBytes, sizeof(Assignment::Type)); + memcpy(&assignmentType, packet.data() + headerBytes, sizeof(Assignment::Type)); switch (assignmentType) { case Assignment::AudioMixerType: - return new AudioMixer(dataBuffer, numBytes); + return new AudioMixer(packet); case Assignment::AvatarMixerType: - return new AvatarMixer(dataBuffer, numBytes); + return new AvatarMixer(packet); case Assignment::AgentType: - return new Agent(dataBuffer, numBytes); + return new Agent(packet); case Assignment::VoxelServerType: - return new VoxelServer(dataBuffer, numBytes); + return new VoxelServer(packet); case Assignment::ParticleServerType: - return new ParticleServer(dataBuffer, numBytes); + return new ParticleServer(packet); case Assignment::MetavoxelServerType: - return new MetavoxelServer(dataBuffer, numBytes); + return new MetavoxelServer(packet); default: return NULL; } diff --git a/assignment-client/src/AssignmentFactory.h b/assignment-client/src/AssignmentFactory.h index 4605d961ec..9eff29a468 100644 --- a/assignment-client/src/AssignmentFactory.h +++ b/assignment-client/src/AssignmentFactory.h @@ -13,7 +13,7 @@ class AssignmentFactory { public: - static ThreadedAssignment* unpackAssignment(const unsigned char* dataBuffer, int numBytes); + static ThreadedAssignment* unpackAssignment(const QByteArray& packet); }; #endif /* defined(__hifi__AssignmentFactory__) */ diff --git a/assignment-client/src/audio/AudioMixer.cpp b/assignment-client/src/audio/AudioMixer.cpp index 705a877a00..6a721824f3 100644 --- a/assignment-client/src/audio/AudioMixer.cpp +++ b/assignment-client/src/audio/AudioMixer.cpp @@ -37,7 +37,6 @@ #include #include #include -#include #include #include #include @@ -61,8 +60,8 @@ void attachNewBufferToNode(Node *newNode) { } } -AudioMixer::AudioMixer(const unsigned char* dataBuffer, int numBytes) : - ThreadedAssignment(dataBuffer, numBytes) +AudioMixer::AudioMixer(const QByteArray& packet) : + ThreadedAssignment(packet) { } @@ -210,18 +209,19 @@ void AudioMixer::prepareMixForListeningNode(Node* node) { void AudioMixer::processDatagram(const QByteArray& dataByteArray, const HifiSockAddr& senderSockAddr) { // pull any new audio data from nodes off of the network stack - if (dataByteArray[0] == PACKET_TYPE_MICROPHONE_AUDIO_NO_ECHO - || dataByteArray[0] == PACKET_TYPE_MICROPHONE_AUDIO_WITH_ECHO - || dataByteArray[0] == PACKET_TYPE_INJECT_AUDIO) { - QUuid nodeUUID = QUuid::fromRfc4122(dataByteArray.mid(numBytesForPacketHeader((unsigned char*) dataByteArray.data()), - NUM_BYTES_RFC4122_UUID)); + PacketType mixerPacketType = packetTypeForPacket(dataByteArray); + if (mixerPacketType == PacketTypeMicrophoneAudioNoEcho + || mixerPacketType == PacketTypeMicrophoneAudioWithEcho + || mixerPacketType == PacketTypeInjectAudio) { + QUuid nodeUUID; + deconstructPacketHeader(dataByteArray, nodeUUID); NodeList* nodeList = NodeList::getInstance(); SharedNodePointer matchingNode = nodeList->nodeWithUUID(nodeUUID); if (matchingNode) { - nodeList->updateNodeWithData(matchingNode.data(), senderSockAddr, (unsigned char*) dataByteArray.data(), dataByteArray.size()); + nodeList->updateNodeWithData(matchingNode.data(), senderSockAddr, dataByteArray); if (!matchingNode->getActiveSocket()) { // we don't have an active socket for this node, but they're talking to us @@ -231,7 +231,7 @@ void AudioMixer::processDatagram(const QByteArray& dataByteArray, const HifiSock } } else { // let processNodeData handle it. - NodeList::getInstance()->processNodeData(senderSockAddr, (unsigned char*) dataByteArray.data(), dataByteArray.size()); + NodeList::getInstance()->processNodeData(senderSockAddr, dataByteArray); } } @@ -250,14 +250,14 @@ void AudioMixer::run() { gettimeofday(&startTime, NULL); - int numBytesPacketHeader = numBytesForPacketHeader((unsigned char*) &PACKET_TYPE_MIXED_AUDIO); + int numBytesPacketHeader = numBytesForPacketHeaderGivenPacketType(PacketTypeMixedAudio); // note: Visual Studio 2010 doesn't support variable sized local arrays #ifdef _WIN32 unsigned char clientPacket[MAX_PACKET_SIZE]; #else unsigned char clientPacket[NETWORK_BUFFER_LENGTH_BYTES_STEREO + numBytesPacketHeader]; #endif - populateTypeAndVersion(clientPacket, PACKET_TYPE_MIXED_AUDIO); + populatePacketHeader(reinterpret_cast(clientPacket), PacketTypeMixedAudio); while (!_isFinished) { diff --git a/assignment-client/src/audio/AudioMixer.h b/assignment-client/src/audio/AudioMixer.h index 7326e1a161..2d42a6b629 100644 --- a/assignment-client/src/audio/AudioMixer.h +++ b/assignment-client/src/audio/AudioMixer.h @@ -20,7 +20,7 @@ class AvatarAudioRingBuffer; class AudioMixer : public ThreadedAssignment { Q_OBJECT public: - AudioMixer(const unsigned char* dataBuffer, int numBytes); + AudioMixer(const QByteArray& packet); public slots: /// threaded run of assignment void run(); diff --git a/assignment-client/src/audio/AudioMixerClientData.cpp b/assignment-client/src/audio/AudioMixerClientData.cpp index 0838de4f45..a41889e77c 100644 --- a/assignment-client/src/audio/AudioMixerClientData.cpp +++ b/assignment-client/src/audio/AudioMixerClientData.cpp @@ -31,9 +31,10 @@ AvatarAudioRingBuffer* AudioMixerClientData::getAvatarAudioRingBuffer() const { return NULL; } -int AudioMixerClientData::parseData(unsigned char* packetData, int numBytes) { - if (packetData[0] == PACKET_TYPE_MICROPHONE_AUDIO_WITH_ECHO - || packetData[0] == PACKET_TYPE_MICROPHONE_AUDIO_NO_ECHO) { +int AudioMixerClientData::parseData(const QByteArray& packet) { + PacketType packetType = packetTypeForPacket(packet); + if (packetType == PacketTypeMicrophoneAudioWithEcho + || packetType == PacketTypeMicrophoneAudioNoEcho) { // grab the AvatarAudioRingBuffer from the vector (or create it if it doesn't exist) AvatarAudioRingBuffer* avatarRingBuffer = getAvatarAudioRingBuffer(); @@ -45,14 +46,12 @@ int AudioMixerClientData::parseData(unsigned char* packetData, int numBytes) { } // ask the AvatarAudioRingBuffer instance to parse the data - avatarRingBuffer->parseData(packetData, numBytes); + avatarRingBuffer->parseData(packet); } else { // this is injected audio // grab the stream identifier for this injected audio - QByteArray rfcUUID = QByteArray((char*) packetData + numBytesForPacketHeader(packetData) + NUM_BYTES_RFC4122_UUID, - NUM_BYTES_RFC4122_UUID); - QUuid streamIdentifier = QUuid::fromRfc4122(rfcUUID); + QUuid streamIdentifier = QUuid::fromRfc4122(packet.mid(numBytesForPacketHeader(packet), NUM_BYTES_RFC4122_UUID)); InjectedAudioRingBuffer* matchingInjectedRingBuffer = NULL; @@ -69,7 +68,7 @@ int AudioMixerClientData::parseData(unsigned char* packetData, int numBytes) { _ringBuffers.push_back(matchingInjectedRingBuffer); } - matchingInjectedRingBuffer->parseData(packetData, numBytes); + matchingInjectedRingBuffer->parseData(packet); } return 0; diff --git a/assignment-client/src/audio/AudioMixerClientData.h b/assignment-client/src/audio/AudioMixerClientData.h index 05cfa51e5f..8031dfec3e 100644 --- a/assignment-client/src/audio/AudioMixerClientData.h +++ b/assignment-client/src/audio/AudioMixerClientData.h @@ -23,7 +23,7 @@ public: const std::vector getRingBuffers() const { return _ringBuffers; } AvatarAudioRingBuffer* getAvatarAudioRingBuffer() const; - int parseData(unsigned char* packetData, int numBytes); + int parseData(const QByteArray& packet); void checkBuffersBeforeFrameSend(int jitterBufferLengthSamples); void pushBuffersAfterFrameSend(); private: diff --git a/assignment-client/src/audio/AvatarAudioRingBuffer.cpp b/assignment-client/src/audio/AvatarAudioRingBuffer.cpp index 64d71d9836..4b1907efb8 100644 --- a/assignment-client/src/audio/AvatarAudioRingBuffer.cpp +++ b/assignment-client/src/audio/AvatarAudioRingBuffer.cpp @@ -15,7 +15,7 @@ AvatarAudioRingBuffer::AvatarAudioRingBuffer() : } -int AvatarAudioRingBuffer::parseData(unsigned char* sourceBuffer, int numBytes) { - _shouldLoopbackForNode = (sourceBuffer[0] == PACKET_TYPE_MICROPHONE_AUDIO_WITH_ECHO); - return PositionalAudioRingBuffer::parseData(sourceBuffer, numBytes); +int AvatarAudioRingBuffer::parseData(const QByteArray& packet) { + _shouldLoopbackForNode = (packetTypeForPacket(packet) == PacketTypeMicrophoneAudioWithEcho); + return PositionalAudioRingBuffer::parseData(packet); } \ No newline at end of file diff --git a/assignment-client/src/audio/AvatarAudioRingBuffer.h b/assignment-client/src/audio/AvatarAudioRingBuffer.h index 15542383fb..0d4f28467b 100644 --- a/assignment-client/src/audio/AvatarAudioRingBuffer.h +++ b/assignment-client/src/audio/AvatarAudioRingBuffer.h @@ -17,7 +17,7 @@ class AvatarAudioRingBuffer : public PositionalAudioRingBuffer { public: AvatarAudioRingBuffer(); - int parseData(unsigned char* sourceBuffer, int numBytes); + int parseData(const QByteArray& packet); private: // disallow copying of AvatarAudioRingBuffer objects AvatarAudioRingBuffer(const AvatarAudioRingBuffer&); diff --git a/assignment-client/src/avatars/AvatarMixer.cpp b/assignment-client/src/avatars/AvatarMixer.cpp index 64e93fd751..bb5654ddb7 100644 --- a/assignment-client/src/avatars/AvatarMixer.cpp +++ b/assignment-client/src/avatars/AvatarMixer.cpp @@ -27,24 +27,13 @@ const char AVATAR_MIXER_LOGGING_NAME[] = "avatar-mixer"; const unsigned int AVATAR_DATA_SEND_INTERVAL_USECS = (1 / 60.0) * 1000 * 1000; -AvatarMixer::AvatarMixer(const unsigned char* dataBuffer, int numBytes) : - ThreadedAssignment(dataBuffer, numBytes) +AvatarMixer::AvatarMixer(const QByteArray& packet) : + ThreadedAssignment(packet) { // make sure we hear about node kills so we can tell the other nodes connect(NodeList::getInstance(), &NodeList::nodeKilled, this, &AvatarMixer::nodeKilled); } -unsigned char* addNodeToBroadcastPacket(unsigned char *currentPosition, Node *nodeToAdd) { - QByteArray rfcUUID = nodeToAdd->getUUID().toRfc4122(); - memcpy(currentPosition, rfcUUID.constData(), rfcUUID.size()); - currentPosition += rfcUUID.size(); - - AvatarData *nodeData = (AvatarData *)nodeToAdd->getLinkedData(); - currentPosition += nodeData->getBroadcastData(currentPosition); - - return currentPosition; -} - void attachAvatarDataToNode(Node* newNode) { if (newNode->getLinkedData() == NULL) { newNode->setLinkedData(new AvatarData()); @@ -59,11 +48,10 @@ void attachAvatarDataToNode(Node* newNode) { // determine which avatars are included in the packet stream // 4) we should optimize the avatar data format to be more compact (100 bytes is pretty wasteful). void broadcastAvatarData() { - static unsigned char broadcastPacket[MAX_PACKET_SIZE]; - static unsigned char avatarDataBuffer[MAX_PACKET_SIZE]; - int numHeaderBytes = populateTypeAndVersion(broadcastPacket, PACKET_TYPE_BULK_AVATAR_DATA); - unsigned char* currentBufferPosition = broadcastPacket + numHeaderBytes; - int packetLength = currentBufferPosition - broadcastPacket; + static QByteArray mixedAvatarByteArray; + + int numPacketHeaderBytes = populatePacketHeader(mixedAvatarByteArray, PacketTypeBulkAvatarData); + int packetsSent = 0; NodeList* nodeList = NodeList::getInstance(); @@ -72,45 +60,39 @@ void broadcastAvatarData() { if (node->getLinkedData() && node->getType() == NODE_TYPE_AGENT && node->getActiveSocket()) { // reset packet pointers for this node - currentBufferPosition = broadcastPacket + numHeaderBytes; - packetLength = currentBufferPosition - broadcastPacket; + mixedAvatarByteArray.resize(numPacketHeaderBytes); // this is an AGENT we have received head data from // send back a packet with other active node data to this node foreach (const SharedNodePointer& otherNode, nodeList->getNodeHash()) { if (otherNode->getLinkedData() && otherNode->getUUID() != node->getUUID()) { - unsigned char* avatarDataEndpoint = addNodeToBroadcastPacket((unsigned char*)&avatarDataBuffer[0], - otherNode.data()); - int avatarDataLength = avatarDataEndpoint - (unsigned char*)&avatarDataBuffer; + QByteArray avatarByteArray; + avatarByteArray.append(otherNode->getUUID().toRfc4122()); - if (avatarDataLength + packetLength <= MAX_PACKET_SIZE) { - memcpy(currentBufferPosition, &avatarDataBuffer[0], avatarDataLength); - packetLength += avatarDataLength; - currentBufferPosition += avatarDataLength; - } else { + + AvatarData *nodeData = (AvatarData *)otherNode->getLinkedData(); + avatarByteArray.append(nodeData->toByteArray()); + + if (avatarByteArray.size() + mixedAvatarByteArray.size() > MAX_PACKET_SIZE) { packetsSent++; //printf("packetsSent=%d packetLength=%d\n", packetsSent, packetLength); - nodeList->getNodeSocket().writeDatagram((char*) broadcastPacket, - currentBufferPosition - broadcastPacket, + nodeList->getNodeSocket().writeDatagram(mixedAvatarByteArray, node->getActiveSocket()->getAddress(), node->getActiveSocket()->getPort()); // reset the packet - currentBufferPosition = broadcastPacket + numHeaderBytes; - packetLength = currentBufferPosition - broadcastPacket; - - // copy the avatar that didn't fit into the next packet - memcpy(currentBufferPosition, &avatarDataBuffer[0], avatarDataLength); - packetLength += avatarDataLength; - currentBufferPosition += avatarDataLength; + mixedAvatarByteArray.resize(numPacketHeaderBytes); } + + // copy the avatar into the mixedAvatarByteArray packet + mixedAvatarByteArray.append(avatarByteArray); } } packetsSent++; //printf("packetsSent=%d packetLength=%d\n", packetsSent, packetLength); - nodeList->getNodeSocket().writeDatagram((char*) broadcastPacket, currentBufferPosition - broadcastPacket, + nodeList->getNodeSocket().writeDatagram(mixedAvatarByteArray, node->getActiveSocket()->getAddress(), node->getActiveSocket()->getPort()); } @@ -122,13 +104,10 @@ void AvatarMixer::nodeKilled(SharedNodePointer killedNode) { && killedNode->getLinkedData()) { // this was an avatar we were sending to other people // send a kill packet for it to our other nodes - unsigned char packetData[MAX_PACKET_SIZE]; - int numHeaderBytes = populateTypeAndVersion(packetData, PACKET_TYPE_KILL_AVATAR); + QByteArray killPacket = byteArrayWithPopluatedHeader(PacketTypeKillAvatar); + killPacket += killedNode->getUUID().toRfc4122(); - QByteArray rfcUUID = killedNode->getUUID().toRfc4122(); - memcpy(packetData + numHeaderBytes, rfcUUID.constData(), rfcUUID.size()); - - NodeList::getInstance()->broadcastToNodes(packetData, numHeaderBytes + NUM_BYTES_RFC4122_UUID, + NodeList::getInstance()->broadcastToNodes(killPacket, QSet() << NODE_TYPE_AGENT); } } @@ -137,29 +116,28 @@ void AvatarMixer::processDatagram(const QByteArray& dataByteArray, const HifiSoc NodeList* nodeList = NodeList::getInstance(); - switch (dataByteArray[0]) { - case PACKET_TYPE_HEAD_DATA: { - QUuid nodeUUID = QUuid::fromRfc4122(dataByteArray.mid(numBytesForPacketHeader((unsigned char*) dataByteArray.data()), - NUM_BYTES_RFC4122_UUID)); + switch (packetTypeForPacket(dataByteArray)) { + case PacketTypeAvatarData: { + QUuid nodeUUID; + deconstructPacketHeader(dataByteArray, nodeUUID); // add or update the node in our list SharedNodePointer avatarNode = nodeList->nodeWithUUID(nodeUUID); if (avatarNode) { // parse positional data from an node - nodeList->updateNodeWithData(avatarNode.data(), senderSockAddr, - (unsigned char*) dataByteArray.data(), dataByteArray.size()); + nodeList->updateNodeWithData(avatarNode.data(), senderSockAddr, dataByteArray); } break; } - case PACKET_TYPE_KILL_AVATAR: { + case PacketTypeKillAvatar: { nodeList->processKillNode(dataByteArray); break; } default: // hand this off to the NodeList - nodeList->processNodeData(senderSockAddr, (unsigned char*) dataByteArray.data(), dataByteArray.size()); + nodeList->processNodeData(senderSockAddr, dataByteArray); break; } diff --git a/assignment-client/src/avatars/AvatarMixer.h b/assignment-client/src/avatars/AvatarMixer.h index 2da0ed98eb..92ab1a5c53 100644 --- a/assignment-client/src/avatars/AvatarMixer.h +++ b/assignment-client/src/avatars/AvatarMixer.h @@ -14,7 +14,7 @@ /// Handles assignments of type AvatarMixer - distribution of avatar data to various clients class AvatarMixer : public ThreadedAssignment { public: - AvatarMixer(const unsigned char* dataBuffer, int numBytes); + AvatarMixer(const QByteArray& packet); public slots: /// runs the avatar mixer diff --git a/assignment-client/src/metavoxels/MetavoxelServer.cpp b/assignment-client/src/metavoxels/MetavoxelServer.cpp index af982abf9b..9fee6f3e2c 100644 --- a/assignment-client/src/metavoxels/MetavoxelServer.cpp +++ b/assignment-client/src/metavoxels/MetavoxelServer.cpp @@ -17,8 +17,8 @@ const int SEND_INTERVAL = 50; -MetavoxelServer::MetavoxelServer(const unsigned char* dataBuffer, int numBytes) : - ThreadedAssignment(dataBuffer, numBytes), +MetavoxelServer::MetavoxelServer(const QByteArray& packet) : + ThreadedAssignment(packet), _data(new MetavoxelData()) { _sendTimer.setSingleShot(true); @@ -40,12 +40,12 @@ void MetavoxelServer::run() { void MetavoxelServer::processDatagram(const QByteArray& dataByteArray, const HifiSockAddr& senderSockAddr) { switch (dataByteArray.at(0)) { - case PACKET_TYPE_METAVOXEL_DATA: + case PacketTypeMetavoxelData: processData(dataByteArray, senderSockAddr); break; default: - NodeList::getInstance()->processNodeData(senderSockAddr, (unsigned char*)dataByteArray.data(), dataByteArray.size()); + NodeList::getInstance()->processNodeData(senderSockAddr, dataByteArray); break; } } diff --git a/assignment-client/src/metavoxels/MetavoxelServer.h b/assignment-client/src/metavoxels/MetavoxelServer.h index 407c520116..862d5a8d18 100644 --- a/assignment-client/src/metavoxels/MetavoxelServer.h +++ b/assignment-client/src/metavoxels/MetavoxelServer.h @@ -28,7 +28,7 @@ class MetavoxelServer : public ThreadedAssignment { public: - MetavoxelServer(const unsigned char* dataBuffer, int numBytes); + MetavoxelServer(const QByteArray& packet); const MetavoxelDataPointer& getData() const { return _data; } diff --git a/data-server/src/DataServer.cpp b/data-server/src/DataServer.cpp index c59749ed08..173f42f33a 100644 --- a/data-server/src/DataServer.cpp +++ b/data-server/src/DataServer.cpp @@ -9,6 +9,7 @@ #include #include +#include #include #include "DataServer.h" @@ -51,66 +52,59 @@ DataServer::~DataServer() { const int MAX_PACKET_SIZE = 1500; void DataServer::readPendingDatagrams() { - qint64 receivedBytes = 0; - static unsigned char packetData[MAX_PACKET_SIZE]; - + QByteArray receivedPacket; HifiSockAddr senderSockAddr; - while (_socket.hasPendingDatagrams() && - (receivedBytes = _socket.readDatagram(reinterpret_cast(packetData), MAX_PACKET_SIZE, - senderSockAddr.getAddressPointer(), senderSockAddr.getPortPointer()))) { - if ((packetData[0] == PACKET_TYPE_DATA_SERVER_PUT || packetData[0] == PACKET_TYPE_DATA_SERVER_GET) && - packetVersionMatch(packetData, senderSockAddr)) { - - int readBytes = numBytesForPacketHeader(packetData); + while (_socket.hasPendingDatagrams()) { + receivedPacket.resize(_socket.pendingDatagramSize()); + _socket.readDatagram(receivedPacket.data(), _socket.pendingDatagramSize()); + + PacketType requestType = packetTypeForPacket(receivedPacket); + + if ((requestType == PacketTypeDataServerPut || requestType == PacketTypeDataServerGet) && + packetVersionMatch(receivedPacket)) { + + QDataStream packetStream(receivedPacket); + int numReceivedHeaderBytes = numBytesForPacketHeader(receivedPacket); + packetStream.skipRawData(numReceivedHeaderBytes); // pull the sequence number used for this packet quint8 sequenceNumber = 0; - memcpy(&sequenceNumber, packetData + readBytes, sizeof(sequenceNumber)); - readBytes += sizeof(sequenceNumber); - + + packetStream >> sequenceNumber; + // pull the UUID that we will need as part of the key - QString uuidString(reinterpret_cast(packetData + readBytes)); - QUuid parsedUUID(uuidString); + QString userString; + packetStream >> userString; + QUuid parsedUUID(userString); if (parsedUUID.isNull()) { // we failed to parse a UUID, this means the user has sent us a username - QString username(reinterpret_cast(packetData + readBytes)); - readBytes += username.size() + sizeof('\0'); - // ask redis for the UUID for this user - redisReply* reply = (redisReply*) redisCommand(_redis, "GET user:%s", qPrintable(username)); + redisReply* reply = (redisReply*) redisCommand(_redis, "GET user:%s", qPrintable(userString)); if (reply->type == REDIS_REPLY_STRING) { parsedUUID = QUuid(QString(reply->str)); } if (!parsedUUID.isNull()) { - qDebug() << "Found UUID" << parsedUUID << "for username" << username; + qDebug() << "Found UUID" << parsedUUID << "for username" << userString; } else { - qDebug() << "Failed UUID lookup for username" << username; + qDebug() << "Failed UUID lookup for username" << userString; } freeReplyObject(reply); reply = NULL; - } else { - readBytes += uuidString.size() + sizeof('\0'); } if (!parsedUUID.isNull()) { - // pull the number of keys the user has sent - unsigned char numKeys = packetData[readBytes++]; - - if (packetData[0] == PACKET_TYPE_DATA_SERVER_PUT) { + if (requestType == PacketTypeDataServerPut) { - // pull the key that specifies the data the user is putting/getting - QString dataKey(reinterpret_cast(packetData + readBytes)); - readBytes += dataKey.size() + sizeof('\0'); + // pull the key and value that specifies the data the user is putting/getting + QString dataKey, dataValue; - // grab the string value the user wants us to put, null terminate it - QString dataValue(reinterpret_cast(packetData + readBytes)); - readBytes += dataValue.size() + sizeof('\0'); + packetStream >> dataKey >> dataValue; qDebug("Sending command to redis: SET uuid:%s:%s %s", qPrintable(uuidStringWithoutCurlyBraces(parsedUUID)), @@ -122,9 +116,12 @@ void DataServer::readPendingDatagrams() { if (reply->type == REDIS_REPLY_STATUS && strcmp("OK", reply->str) == 0) { // if redis stored the value successfully reply back with a confirm - // which is the sent packet with the header replaced - packetData[0] = PACKET_TYPE_DATA_SERVER_CONFIRM; - _socket.writeDatagram(reinterpret_cast(packetData), receivedBytes, + // which is a reply packet with the sequence number + QByteArray replyPacket = byteArrayWithPopluatedHeader(PacketTypeDataServerConfirm); + + replyPacket.append(sequenceNumber); + + _socket.writeDatagram(replyPacket, senderSockAddr.getAddress(), senderSockAddr.getPort()); } @@ -132,66 +129,49 @@ void DataServer::readPendingDatagrams() { } else { // setup a send packet with the returned data // leverage the packetData sent by overwriting and appending - int numSendPacketBytes = receivedBytes; + QByteArray sendPacket = byteArrayWithPopluatedHeader(PacketTypeDataServerSend); - packetData[0] = PACKET_TYPE_DATA_SERVER_SEND; - - if (strcmp((char*) packetData + readBytes, "uuid") != 0) { + if (!receivedPacket.mid(numReceivedHeaderBytes).startsWith("uuid")) { const char MULTI_KEY_VALUE_SEPARATOR = '|'; - // the user has sent one or more keys - make the associated requests - for (int j = 0; j < numKeys; j++) { - - // pull the key that specifies the data the user is putting/getting, null terminate it - int numDataKeyBytes = 0; - - // look for the key separator or the null terminator - while (packetData[readBytes + numDataKeyBytes] != MULTI_KEY_VALUE_SEPARATOR - && packetData[readBytes + numDataKeyBytes] != '\0') { - numDataKeyBytes++; - } - - QString dataKey(QByteArray(reinterpret_cast(packetData + readBytes), numDataKeyBytes)); - readBytes += dataKey.size() + sizeof('\0'); - + // pull the key that specifies the data the user is putting/getting, null terminate it + QString keyListString(receivedPacket.mid(numReceivedHeaderBytes)); + QStringList keyList = keyListString.split(MULTI_KEY_VALUE_SEPARATOR); + + foreach (const QString& dataKey, keyList) { qDebug("Sending command to redis: GET uuid:%s:%s", qPrintable(uuidStringWithoutCurlyBraces(parsedUUID)), qPrintable(dataKey)); redisReply* reply = (redisReply*) redisCommand(_redis, "GET uuid:%s:%s", - qPrintable(uuidStringWithoutCurlyBraces(parsedUUID)), - qPrintable(dataKey)); + qPrintable(uuidStringWithoutCurlyBraces(parsedUUID)), + qPrintable(dataKey)); if (reply->len) { // copy the value that redis returned - memcpy(packetData + numSendPacketBytes, reply->str, reply->len); - numSendPacketBytes += reply->len; + sendPacket.append(reply->str, reply->len); } else { // didn't find a value - insert a space - packetData[numSendPacketBytes++] = ' '; + sendPacket.append(' '); } // add the multi-value separator - packetData[numSendPacketBytes++] = MULTI_KEY_VALUE_SEPARATOR; + sendPacket.append(MULTI_KEY_VALUE_SEPARATOR); freeReplyObject(reply); } // null terminate the packet we're sending back (erases the trailing separator) - packetData[(numSendPacketBytes - 1)] = '\0'; + sendPacket[sendPacket.size() - 1] = '\0'; } else { // user is asking for a UUID matching username, copy the UUID we found - QString uuidString = uuidStringWithoutCurlyBraces(parsedUUID); - memcpy(packetData + numSendPacketBytes, qPrintable(uuidString), uuidString.size() + sizeof('\0')); - numSendPacketBytes += uuidString.size() + sizeof('\0'); + sendPacket.append(uuidStringWithoutCurlyBraces(parsedUUID)); + sendPacket.append('\0'); } // reply back with the send packet - _socket.writeDatagram(reinterpret_cast(packetData), numSendPacketBytes, - senderSockAddr.getAddress(), senderSockAddr.getPort()); - - + _socket.writeDatagram(sendPacket, senderSockAddr.getAddress(), senderSockAddr.getPort()); } } } diff --git a/domain-server/src/DomainServer.cpp b/domain-server/src/DomainServer.cpp index 0ee7cca467..073f788f86 100644 --- a/domain-server/src/DomainServer.cpp +++ b/domain-server/src/DomainServer.cpp @@ -102,39 +102,39 @@ void DomainServer::readAvailableDatagrams() { NodeList* nodeList = NodeList::getInstance(); HifiSockAddr senderSockAddr, nodePublicAddress, nodeLocalAddress; - - static unsigned char packetData[MAX_PACKET_SIZE]; - - static unsigned char broadcastPacket[MAX_PACKET_SIZE]; - - static unsigned char* currentBufferPos; - static unsigned char* startPointer; - - int receivedBytes = 0; + + static QByteArray broadcastPacket = byteArrayWithPopluatedHeader(PacketTypeDomainList); + static int numBroadcastPacketHeaderBytes = broadcastPacket.size(); + + static QByteArray assignmentPacket = byteArrayWithPopluatedHeader(PacketTypeCreateAssignment); + static int numAssignmentPacketHeaderBytes = assignmentPacket.size(); + + QByteArray receivedPacket; + NODE_TYPE nodeType; + QUuid nodeUUID; while (nodeList->getNodeSocket().hasPendingDatagrams()) { - if ((receivedBytes = nodeList->getNodeSocket().readDatagram((char*) packetData, MAX_PACKET_SIZE, - senderSockAddr.getAddressPointer(), - senderSockAddr.getPortPointer())) - && packetVersionMatch((unsigned char*) packetData, senderSockAddr)) { - if (packetData[0] == PACKET_TYPE_DOMAIN_REPORT_FOR_DUTY || packetData[0] == PACKET_TYPE_DOMAIN_LIST_REQUEST) { + receivedPacket.resize(nodeList->getNodeSocket().pendingDatagramSize()); + nodeList->getNodeSocket().readDatagram(receivedPacket.data(), receivedPacket.size(), + senderSockAddr.getAddressPointer(), senderSockAddr.getPortPointer()); + + if (packetVersionMatch(receivedPacket)) { + PacketType requestType = packetTypeForPacket(receivedPacket); + if (requestType == PacketTypeDomainListRequest) { + // this is an RFD or domain list request packet, and there is a version match - - int numBytesSenderHeader = numBytesForPacketHeader((unsigned char*) packetData); - - NODE_TYPE nodeType = *(packetData + numBytesSenderHeader); - - int packetIndex = numBytesSenderHeader + sizeof(NODE_TYPE); - QUuid nodeUUID = QUuid::fromRfc4122(QByteArray(((char*) packetData + packetIndex), NUM_BYTES_RFC4122_UUID)); - packetIndex += NUM_BYTES_RFC4122_UUID; - - int numBytesPrivateSocket = HifiSockAddr::unpackSockAddr(packetData + packetIndex, nodePublicAddress); - packetIndex += numBytesPrivateSocket; - + QDataStream packetStream(receivedPacket); + packetStream.skipRawData(numBytesForPacketHeader(receivedPacket)); + + deconstructPacketHeader(receivedPacket, nodeUUID); + packetStream >> nodeType; + + packetStream >> nodePublicAddress >> nodeLocalAddress; + if (nodePublicAddress.getAddress().isNull()) { // this node wants to use us its STUN server // so set the node public address to whatever we perceive the public address to be - + // if the sender is on our box then leave its public address to 0 so that // other users attempt to reach it on the same address they have for the domain-server if (senderSockAddr.getAddress().isLoopback()) { @@ -143,20 +143,14 @@ void DomainServer::readAvailableDatagrams() { nodePublicAddress.setAddress(senderSockAddr.getAddress()); } } - - int numBytesPublicSocket = HifiSockAddr::unpackSockAddr(packetData + packetIndex, nodeLocalAddress); - packetIndex += numBytesPublicSocket; - - const char STATICALLY_ASSIGNED_NODES[] = { - NODE_TYPE_AUDIO_MIXER, - NODE_TYPE_AVATAR_MIXER, - NODE_TYPE_VOXEL_SERVER, - NODE_TYPE_METAVOXEL_SERVER - }; - + + const QSet STATICALLY_ASSIGNED_NODES = QSet() << NODE_TYPE_AUDIO_MIXER + << NODE_TYPE_AVATAR_MIXER << NODE_TYPE_VOXEL_SERVER << NODE_TYPE_PARTICLE_SERVER + << NODE_TYPE_METAVOXEL_SERVER; + Assignment* matchingStaticAssignment = NULL; - - if (memchr(STATICALLY_ASSIGNED_NODES, nodeType, sizeof(STATICALLY_ASSIGNED_NODES)) == NULL + + if (!STATICALLY_ASSIGNED_NODES.contains(nodeType) || ((matchingStaticAssignment = matchingStaticAssignmentForCheckIn(nodeUUID, nodeType)) || checkInWithUUIDMatchesExistingNode(nodePublicAddress, nodeLocalAddress, @@ -166,80 +160,81 @@ void DomainServer::readAvailableDatagrams() { nodeType, nodePublicAddress, nodeLocalAddress); - + + // resize our broadcast packet in preparation to set it up again + broadcastPacket.resize(numBroadcastPacketHeaderBytes); + if (matchingStaticAssignment) { // this was a newly added node with a matching static assignment - + if (_hasCompletedRestartHold) { // remove the matching assignment from the assignment queue so we don't take the next check in removeAssignmentFromQueue(matchingStaticAssignment); } - + // set the linked data for this node to a copy of the matching assignment // so we can re-queue it should the node die Assignment* nodeCopyOfMatchingAssignment = new Assignment(*matchingStaticAssignment); - + checkInNode->setLinkedData(nodeCopyOfMatchingAssignment); } - - int numHeaderBytes = populateTypeAndVersion(broadcastPacket, PACKET_TYPE_DOMAIN); - - currentBufferPos = broadcastPacket + numHeaderBytes; - startPointer = currentBufferPos; - - unsigned char* nodeTypesOfInterest = packetData + packetIndex + sizeof(unsigned char); - int numInterestTypes = *(nodeTypesOfInterest - 1); - + + + quint8 numInterestTypes = 0; + packetStream >> numInterestTypes; + + NODE_TYPE* nodeTypesOfInterest = reinterpret_cast(receivedPacket.data() + + packetStream.device()->pos()); + if (numInterestTypes > 0) { + QDataStream broadcastDataStream(&broadcastPacket, QIODevice::Append); + // if the node has sent no types of interest, assume they want nothing but their own ID back foreach (const SharedNodePointer& node, nodeList->getNodeHash()) { if (node->getUUID() != nodeUUID && memchr(nodeTypesOfInterest, node->getType(), numInterestTypes)) { - + // don't send avatar nodes to other avatars, that will come from avatar mixer - if (nodeType != NODE_TYPE_AGENT || node->getType() != NODE_TYPE_AGENT) { - currentBufferPos = addNodeToBroadcastPacket(currentBufferPos, node.data()); - } - + broadcastDataStream << *node.data(); } } } - + // update last receive to now uint64_t timeNow = usecTimestampNow(); checkInNode->setLastHeardMicrostamp(timeNow); - + // send the constructed list back to this node - nodeList->getNodeSocket().writeDatagram((char*) broadcastPacket, - (currentBufferPos - startPointer) + numHeaderBytes, + nodeList->getNodeSocket().writeDatagram(broadcastPacket, senderSockAddr.getAddress(), senderSockAddr.getPort()); } - } else if (packetData[0] == PACKET_TYPE_REQUEST_ASSIGNMENT) { - + } else if (requestType == PacketTypeRequestAssignment) { + if (_assignmentQueue.size() > 0) { // construct the requested assignment from the packet data - Assignment requestAssignment(packetData, receivedBytes); - + Assignment requestAssignment(receivedPacket); + qDebug("Received a request for assignment type %i from %s.", requestAssignment.getType(), qPrintable(senderSockAddr.getAddress().toString())); - + Assignment* assignmentToDeploy = deployableAssignmentForRequest(requestAssignment); - + if (assignmentToDeploy) { - // give this assignment out, either the type matches or the requestor said they will take any - int numHeaderBytes = populateTypeAndVersion(broadcastPacket, PACKET_TYPE_CREATE_ASSIGNMENT); - int numAssignmentBytes = assignmentToDeploy->packToBuffer(broadcastPacket + numHeaderBytes); - - nodeList->getNodeSocket().writeDatagram((char*) broadcastPacket, numHeaderBytes + numAssignmentBytes, + assignmentPacket.resize(numAssignmentPacketHeaderBytes); + QDataStream assignmentStream(&assignmentPacket, QIODevice::Append); + + assignmentStream << *assignmentToDeploy; + + nodeList->getNodeSocket().writeDatagram(assignmentPacket, senderSockAddr.getAddress(), senderSockAddr.getPort()); - + if (assignmentToDeploy->getNumberOfInstances() == 0) { // there are no more instances of this script to send out, delete it delete assignmentToDeploy; } } - + } else { qDebug() << "Received an invalid assignment request from" << senderSockAddr.getAddress(); } @@ -278,8 +273,8 @@ QJsonObject jsonObjectForNode(Node* node) { nodeJson[JSON_KEY_LOCAL_SOCKET] = jsonForSocket(node->getLocalSocket()); // if the node has pool information, add it - if (node->getLinkedData() && ((Assignment*) node->getLinkedData())->hasPool()) { - nodeJson[JSON_KEY_POOL] = QString(((Assignment*) node->getLinkedData())->getPool()); + if (node->getLinkedData() && !((Assignment*) node->getLinkedData())->getPool().isEmpty()) { + nodeJson[JSON_KEY_POOL] = ((Assignment*) node->getLinkedData())->getPool(); } return nodeJson; @@ -386,8 +381,8 @@ bool DomainServer::handleHTTPRequest(HTTPConnection* connection, const QString& queuedAssignmentJSON[JSON_KEY_TYPE] = QString((*assignment)->getTypeName()); // if the assignment has a pool, add it - if ((*assignment)->hasPool()) { - queuedAssignmentJSON[JSON_KEY_POOL] = QString((*assignment)->getPool()); + if (!(*assignment)->getPool().isEmpty()) { + queuedAssignmentJSON[JSON_KEY_POOL] = (*assignment)->getPool(); } // add this queued assignment to the JSON @@ -538,21 +533,6 @@ void DomainServer::nodeKilled(SharedNodePointer node) { } } -unsigned char* DomainServer::addNodeToBroadcastPacket(unsigned char* currentPosition, Node* nodeToAdd) { - *currentPosition++ = nodeToAdd->getType(); - - - QByteArray rfcUUID = nodeToAdd->getUUID().toRfc4122(); - memcpy(currentPosition, rfcUUID.constData(), rfcUUID.size()); - currentPosition += rfcUUID.size(); - - currentPosition += HifiSockAddr::packSockAddr(currentPosition, nodeToAdd->getPublicSocket()); - currentPosition += HifiSockAddr::packSockAddr(currentPosition, nodeToAdd->getLocalSocket()); - - // return the new unsigned char * for broadcast packet - return currentPosition; -} - void DomainServer::prepopulateStaticAssignmentFile() { int numFreshStaticAssignments = 0; @@ -595,9 +575,8 @@ void DomainServer::prepopulateStaticAssignmentFile() { Assignment voxelServerAssignment(Assignment::CreateCommand, Assignment::VoxelServerType, (assignmentPool.isEmpty() ? NULL : assignmentPool.toLocal8Bit().constData())); - - int payloadLength = config.length() + sizeof(char); - voxelServerAssignment.setPayload((uchar*)config.toLocal8Bit().constData(), payloadLength); + + voxelServerAssignment.setPayload(config.toUtf8()); freshStaticAssignments[numFreshStaticAssignments++] = voxelServerAssignment; } @@ -637,9 +616,8 @@ void DomainServer::prepopulateStaticAssignmentFile() { Assignment particleServerAssignment(Assignment::CreateCommand, Assignment::ParticleServerType, (assignmentPool.isEmpty() ? NULL : assignmentPool.toLocal8Bit().constData())); - - int payloadLength = config.length() + sizeof(char); - particleServerAssignment.setPayload((uchar*)config.toLocal8Bit().constData(), payloadLength); + + particleServerAssignment.setPayload(config.toLocal8Bit()); freshStaticAssignments[numFreshStaticAssignments++] = particleServerAssignment; } @@ -652,7 +630,7 @@ void DomainServer::prepopulateStaticAssignmentFile() { Assignment& metavoxelAssignment = (freshStaticAssignments[numFreshStaticAssignments++] = Assignment(Assignment::CreateCommand, Assignment::MetavoxelServerType)); if (_metavoxelServerConfig) { - metavoxelAssignment.setPayload((const unsigned char*)_metavoxelServerConfig, strlen(_metavoxelServerConfig)); + metavoxelAssignment.setPayload(QByteArray(_metavoxelServerConfig)); } qDebug() << "Adding" << numFreshStaticAssignments << "static assignments to fresh file."; @@ -708,10 +686,8 @@ Assignment* DomainServer::deployableAssignmentForRequest(Assignment& requestAssi while (assignment != _assignmentQueue.end()) { bool requestIsAllTypes = requestAssignment.getType() == Assignment::AllTypes; bool assignmentTypesMatch = (*assignment)->getType() == requestAssignment.getType(); - bool nietherHasPool = !(*assignment)->hasPool() && !requestAssignment.hasPool(); - bool assignmentPoolsMatch = memcmp((*assignment)->getPool(), - requestAssignment.getPool(), - MAX_ASSIGNMENT_POOL_BYTES) == 0; + bool nietherHasPool = (*assignment)->getPool().isEmpty() && requestAssignment.getPool().isEmpty(); + bool assignmentPoolsMatch = (*assignment)->getPool() == requestAssignment.getPool(); if ((requestIsAllTypes || assignmentTypesMatch) && (nietherHasPool || assignmentPoolsMatch)) { diff --git a/domain-server/src/DomainServer.h b/domain-server/src/DomainServer.h index fed5aaaa43..1c662bcb73 100644 --- a/domain-server/src/DomainServer.h +++ b/domain-server/src/DomainServer.h @@ -47,8 +47,6 @@ private: const QUuid& checkInUUI); void addReleasedAssignmentBackToQueue(Assignment* releasedAssignment); - unsigned char* addNodeToBroadcastPacket(unsigned char* currentPosition, Node* nodeToAdd); - HTTPManager _HTTPManager; QMutex _assignmentQueueMutex; diff --git a/interface/src/Application.cpp b/interface/src/Application.cpp index e2778fd6a8..556bb40bcf 100644 --- a/interface/src/Application.cpp +++ b/interface/src/Application.cpp @@ -49,7 +49,6 @@ #include #include -#include #include #include #include @@ -640,7 +639,7 @@ void Application::resetProfile(const QString& username) { updateWindowTitle(); } -void Application::controlledBroadcastToNodes(unsigned char* broadcastData, size_t dataBytes, +void Application::controlledBroadcastToNodes(const QByteArray& packet, const QSet& destinationNodeTypes) { foreach(NODE_TYPE type, destinationNodeTypes) { // Intercept data to voxel server when voxels are disabled @@ -649,8 +648,7 @@ void Application::controlledBroadcastToNodes(unsigned char* broadcastData, size_ } // Perform the broadcast for one type - int nReceivingNodes = NodeList::getInstance()->broadcastToNodes(broadcastData, dataBytes, - QSet() << type); + int nReceivingNodes = NodeList::getInstance()->broadcastToNodes(packet, QSet() << type); // Feed number of bytes to corresponding channel of the bandwidth meter, if any (done otherwise) BandwidthMeter::ChannelIndex channel; @@ -665,7 +663,7 @@ void Application::controlledBroadcastToNodes(unsigned char* broadcastData, size_ default: continue; } - _bandwidthMeter.outputStream(channel).updateValue(nReceivingNodes * dataBytes); + _bandwidthMeter.outputStream(channel).updateValue(nReceivingNodes * packet.size()); } } @@ -1319,11 +1317,9 @@ void Application::wheelEvent(QWheelEvent* event) { } void Application::sendPingPackets() { - unsigned char pingPacket[MAX_PACKET_SIZE]; - int length = NodeList::getInstance()->fillPingPacket(pingPacket); - - getInstance()->controlledBroadcastToNodes(pingPacket, length, QSet() - << NODE_TYPE_VOXEL_SERVER << NODE_TYPE_PARTICLE_SERVER + QByteArray pingPacket = NodeList::getInstance()->constructPingPacket(); + getInstance()->controlledBroadcastToNodes(pingPacket, QSet() << NODE_TYPE_VOXEL_SERVER + << NODE_TYPE_PARTICLE_SERVER << NODE_TYPE_AUDIO_MIXER << NODE_TYPE_AVATAR_MIXER << NODE_TYPE_METAVOXEL_SERVER); } @@ -1463,7 +1459,7 @@ void Application::removeVoxel(glm::vec3 position, voxel.y = position.y / TREE_SCALE; voxel.z = position.z / TREE_SCALE; voxel.s = scale / TREE_SCALE; - _voxelEditSender.sendVoxelEditMessage(PACKET_TYPE_VOXEL_ERASE, voxel); + _voxelEditSender.sendVoxelEditMessage(PacketTypeVoxelErase, voxel); // delete it locally to see the effect immediately (and in case no voxel server is present) _voxels.deleteVoxelAt(voxel.x, voxel.y, voxel.z, voxel.s); @@ -1484,7 +1480,7 @@ void Application::makeVoxel(glm::vec3 position, voxel.red = red; voxel.green = green; voxel.blue = blue; - PACKET_TYPE message = isDestructive ? PACKET_TYPE_VOXEL_SET_DESTRUCTIVE : PACKET_TYPE_VOXEL_SET; + PacketType message = isDestructive ? PacketTypeVoxelSetDestructive : PacketTypeVoxelSet; _voxelEditSender.sendVoxelEditMessage(message, voxel); // create the voxel locally so it appears immediately @@ -1554,7 +1550,7 @@ bool Application::sendVoxelsOperation(OctreeElement* element, void* extraData) { codeColorBuffer[bytesInCode + RED_INDEX] = voxel->getColor()[RED_INDEX]; codeColorBuffer[bytesInCode + GREEN_INDEX] = voxel->getColor()[GREEN_INDEX]; codeColorBuffer[bytesInCode + BLUE_INDEX] = voxel->getColor()[BLUE_INDEX]; - getInstance()->_voxelEditSender.queueVoxelEditMessage(PACKET_TYPE_VOXEL_SET_DESTRUCTIVE, + getInstance()->_voxelEditSender.queueVoxelEditMessage(PacketTypeVoxelSetDestructive, codeColorBuffer, codeAndColorLength); delete[] codeColorBuffer; @@ -2350,18 +2346,10 @@ void Application::updateAvatar(float deltaTime) { _myAvatar.getHead().setAudioLoudness(_audio.getLastInputLoudness()); // send head/hand data to the avatar mixer and voxel server - unsigned char broadcastString[MAX_PACKET_SIZE]; - unsigned char* endOfBroadcastStringWrite = broadcastString; + QByteArray avatarData = byteArrayWithPopluatedHeader(PacketTypeAvatarData); + avatarData.append(_myAvatar.toByteArray()); - endOfBroadcastStringWrite += populateTypeAndVersion(endOfBroadcastStringWrite, PACKET_TYPE_HEAD_DATA); - - // pack the NodeList owner UUID - endOfBroadcastStringWrite += NodeList::getInstance()->packOwnerUUID(endOfBroadcastStringWrite); - - endOfBroadcastStringWrite += _myAvatar.getBroadcastData(endOfBroadcastStringWrite); - - controlledBroadcastToNodes(broadcastString, endOfBroadcastStringWrite - broadcastString, - QSet() << NODE_TYPE_AVATAR_MIXER); + controlledBroadcastToNodes(avatarData, QSet() << NODE_TYPE_AVATAR_MIXER); // Update _viewFrustum with latest camera and view frustum data... // NOTE: we get this from the view frustum, to make it simpler, since the @@ -2372,11 +2360,11 @@ void Application::updateAvatar(float deltaTime) { loadViewFrustum(_myCamera, _viewFrustum); // Update my voxel servers with my current voxel query... - queryOctree(NODE_TYPE_VOXEL_SERVER, PACKET_TYPE_VOXEL_QUERY, _voxelServerJurisdictions); - queryOctree(NODE_TYPE_PARTICLE_SERVER, PACKET_TYPE_PARTICLE_QUERY, _particleServerJurisdictions); + queryOctree(NODE_TYPE_VOXEL_SERVER, PacketTypeVoxelQuery, _voxelServerJurisdictions); + queryOctree(NODE_TYPE_PARTICLE_SERVER, PacketTypeParticleQuery, _particleServerJurisdictions); } -void Application::queryOctree(NODE_TYPE serverType, PACKET_TYPE packetType, NodeToJurisdictionMap& jurisdictions) { +void Application::queryOctree(NODE_TYPE serverType, PacketType packetType, NodeToJurisdictionMap& jurisdictions) { // if voxels are disabled, then don't send this at all... if (!Menu::getInstance()->isOptionChecked(MenuOption::Voxels)) { @@ -2544,10 +2532,7 @@ void Application::queryOctree(NODE_TYPE serverType, PACKET_TYPE packetType, Node unsigned char* endOfVoxelQueryPacket = voxelQueryPacket; // insert packet type/version and node UUID - endOfVoxelQueryPacket += populateTypeAndVersion(endOfVoxelQueryPacket, packetType); - QByteArray ownerUUID = nodeList->getOwnerUUID().toRfc4122(); - memcpy(endOfVoxelQueryPacket, ownerUUID.constData(), ownerUUID.size()); - endOfVoxelQueryPacket += ownerUUID.size(); + endOfVoxelQueryPacket += populatePacketHeader(reinterpret_cast(endOfVoxelQueryPacket), packetType); // encode the query data... endOfVoxelQueryPacket += _voxelQuery.getBroadcastData(endOfVoxelQueryPacket); @@ -3658,7 +3643,7 @@ bool Application::maybeEditVoxelUnderCursor() { void Application::deleteVoxelUnderCursor() { if (_mouseVoxel.s != 0) { // sending delete to the server is sufficient, server will send new version so we see updates soon enough - _voxelEditSender.sendVoxelEditMessage(PACKET_TYPE_VOXEL_ERASE, _mouseVoxel); + _voxelEditSender.sendVoxelEditMessage(PacketTypeVoxelErase, _mouseVoxel); // delete it locally to see the effect immediately (and in case no voxel server is present) _voxels.deleteVoxelAt(_mouseVoxel.x, _mouseVoxel.y, _mouseVoxel.z, _mouseVoxel.s); @@ -3830,8 +3815,7 @@ void Application::nodeKilled(SharedNodePointer node) { } } -void Application::trackIncomingVoxelPacket(unsigned char* messageData, ssize_t messageLength, - const HifiSockAddr& senderSockAddr, bool wasStatsPacket) { +void Application::trackIncomingVoxelPacket(const QByteArray& packet, const HifiSockAddr& senderSockAddr, bool wasStatsPacket) { // Attempt to identify the sender from it's address. SharedNodePointer serverNode = NodeList::getInstance()->nodeWithAddress(senderSockAddr); @@ -3842,13 +3826,13 @@ void Application::trackIncomingVoxelPacket(unsigned char* messageData, ssize_t m _voxelSceneStatsLock.lockForWrite(); if (_octreeServerSceneStats.find(nodeUUID) != _octreeServerSceneStats.end()) { VoxelSceneStats& stats = _octreeServerSceneStats[nodeUUID]; - stats.trackIncomingOctreePacket(messageData, messageLength, wasStatsPacket, serverNode->getClockSkewUsec()); + stats.trackIncomingOctreePacket(packet, wasStatsPacket, serverNode->getClockSkewUsec()); } _voxelSceneStatsLock.unlock(); } } -int Application::parseOctreeStats(unsigned char* messageData, ssize_t messageLength, const HifiSockAddr& senderSockAddr) { +int Application::parseOctreeStats(const QByteArray& packet, const HifiSockAddr& senderSockAddr) { // But, also identify the sender, and keep track of the contained jurisdiction root for this server SharedNodePointer server = NodeList::getInstance()->nodeWithAddress(senderSockAddr); @@ -3856,7 +3840,7 @@ int Application::parseOctreeStats(unsigned char* messageData, ssize_t messageLen // parse the incoming stats datas stick it in a temporary object for now, while we // determine which server it belongs to VoxelSceneStats temp; - int statsMessageLength = temp.unpackFromMessage(messageData, messageLength); + int statsMessageLength = temp.unpackFromMessage(reinterpret_cast(packet.data()), packet.size()); // quick fix for crash... why would voxelServer be NULL? if (server) { @@ -3865,7 +3849,8 @@ int Application::parseOctreeStats(unsigned char* messageData, ssize_t messageLen // now that we know the node ID, let's add these stats to the stats for that node... _voxelSceneStatsLock.lockForWrite(); if (_octreeServerSceneStats.find(nodeUUID) != _octreeServerSceneStats.end()) { - _octreeServerSceneStats[nodeUUID].unpackFromMessage(messageData, messageLength); + _octreeServerSceneStats[nodeUUID].unpackFromMessage(reinterpret_cast(packet.data()), + packet.size()); } else { _octreeServerSceneStats[nodeUUID] = temp; } diff --git a/interface/src/Application.h b/interface/src/Application.h index defe4dc8aa..db93f7c67f 100644 --- a/interface/src/Application.h +++ b/interface/src/Application.h @@ -175,8 +175,7 @@ public: Profile* getProfile() { return &_profile; } void resetProfile(const QString& username); - void controlledBroadcastToNodes(unsigned char* broadcastData, size_t dataBytes, - const QSet& destinationNodeTypes); + void controlledBroadcastToNodes(const QByteArray& packet, const QSet& destinationNodeTypes); void setupWorldLight(); @@ -299,7 +298,7 @@ private: void renderHighlightVoxel(VoxelDetail voxel); void updateAvatar(float deltaTime); - void queryOctree(NODE_TYPE serverType, PACKET_TYPE packetType, NodeToJurisdictionMap& jurisdictions); + void queryOctree(NODE_TYPE serverType, PacketType packetType, NodeToJurisdictionMap& jurisdictions); void loadViewFrustum(Camera& camera, ViewFrustum& viewFrustum); glm::vec3 getSunDirection(); @@ -477,9 +476,8 @@ private: PieMenu _pieMenu; - int parseOctreeStats(unsigned char* messageData, ssize_t messageLength, const HifiSockAddr& senderAddress); - void trackIncomingVoxelPacket(unsigned char* messageData, ssize_t messageLength, - const HifiSockAddr& senderSockAddr, bool wasStatsPacket); + int parseOctreeStats(const QByteArray& packet, const HifiSockAddr& senderAddress); + void trackIncomingVoxelPacket(const QByteArray& packet, const HifiSockAddr& senderSockAddr, bool wasStatsPacket); NodeToJurisdictionMap _voxelServerJurisdictions; NodeToJurisdictionMap _particleServerJurisdictions; diff --git a/interface/src/Audio.cpp b/interface/src/Audio.cpp index 47ab8b0aba..82c7360d77 100644 --- a/interface/src/Audio.cpp +++ b/interface/src/Audio.cpp @@ -22,7 +22,6 @@ #include #include -#include #include #include #include @@ -285,8 +284,8 @@ void Audio::start() { void Audio::handleAudioInput() { static char monoAudioDataPacket[MAX_PACKET_SIZE]; - static int numBytesPacketHeader = numBytesForPacketHeader((unsigned char*) &PACKET_TYPE_MICROPHONE_AUDIO_NO_ECHO); - static int leadingBytes = numBytesPacketHeader + sizeof(glm::vec3) + sizeof(glm::quat) + NUM_BYTES_RFC4122_UUID; + static int numBytesPacketHeader = numBytesForPacketHeaderGivenPacketType(PacketTypeMicrophoneAudioNoEcho); + static int leadingBytes = numBytesPacketHeader + sizeof(glm::vec3) + sizeof(glm::quat); static int16_t* monoAudioSamples = (int16_t*) (monoAudioDataPacket + leadingBytes); @@ -375,16 +374,10 @@ void Audio::handleAudioInput() { // we need the amount of bytes in the buffer + 1 for type // + 12 for 3 floats for position + float for bearing + 1 attenuation byte - PACKET_TYPE packetType = Menu::getInstance()->isOptionChecked(MenuOption::EchoServerAudio) - ? PACKET_TYPE_MICROPHONE_AUDIO_WITH_ECHO : PACKET_TYPE_MICROPHONE_AUDIO_NO_ECHO; + PacketType packetType = Menu::getInstance()->isOptionChecked(MenuOption::EchoServerAudio) + ? PacketTypeMicrophoneAudioWithEcho : PacketTypeMicrophoneAudioNoEcho; - char* currentPacketPtr = monoAudioDataPacket + populateTypeAndVersion((unsigned char*) monoAudioDataPacket, - packetType); - - // pack Source Data - QByteArray rfcUUID = NodeList::getInstance()->getOwnerUUID().toRfc4122(); - memcpy(currentPacketPtr, rfcUUID.constData(), rfcUUID.size()); - currentPacketPtr += rfcUUID.size(); + char* currentPacketPtr = monoAudioDataPacket + populatePacketHeader(monoAudioDataPacket, packetType); // memcpy the three float positions memcpy(currentPacketPtr, &headPosition, sizeof(headPosition)); @@ -433,7 +426,7 @@ void Audio::addReceivedAudioToBuffer(const QByteArray& audioByteArray) { } } - _ringBuffer.parseData((unsigned char*) audioByteArray.data(), audioByteArray.size()); + _ringBuffer.parseData(audioByteArray); static float networkOutputToOutputRatio = (_desiredOutputFormat.sampleRate() / (float) _outputFormat.sampleRate()) * (_desiredOutputFormat.channelCount() / (float) _outputFormat.channelCount()); diff --git a/interface/src/DatagramProcessor.cpp b/interface/src/DatagramProcessor.cpp index b78bd0c309..e2437e4441 100644 --- a/interface/src/DatagramProcessor.cpp +++ b/interface/src/DatagramProcessor.cpp @@ -26,52 +26,51 @@ void DatagramProcessor::processDatagrams() { "DatagramProcessor::processDatagrams()"); HifiSockAddr senderSockAddr; - ssize_t bytesReceived; - static unsigned char incomingPacket[MAX_PACKET_SIZE]; + static QByteArray incomingPacket; Application* application = Application::getInstance(); + NodeList* nodeList = NodeList::getInstance(); - while (NodeList::getInstance()->getNodeSocket().hasPendingDatagrams() && - (bytesReceived = NodeList::getInstance()->getNodeSocket().readDatagram((char*) incomingPacket, - MAX_PACKET_SIZE, - senderSockAddr.getAddressPointer(), - senderSockAddr.getPortPointer()))) { + while (NodeList::getInstance()->getNodeSocket().hasPendingDatagrams()) { + incomingPacket.resize(nodeList->getNodeSocket().pendingDatagramSize()); + nodeList->getNodeSocket().readDatagram(incomingPacket.data(), incomingPacket.size()); _packetCount++; - _byteCount += bytesReceived; + _byteCount += incomingPacket.size(); - if (packetVersionMatch(incomingPacket, senderSockAddr)) { + if (packetVersionMatch(incomingPacket)) { // only process this packet if we have a match on the packet version - switch (incomingPacket[0]) { - case PACKET_TYPE_TRANSMITTER_DATA_V2: + switch (packetTypeForPacket(incomingPacket)) { + case PacketTypeTransmitterData: // V2 = IOS transmitter app - application->_myTransmitter.processIncomingData(incomingPacket, bytesReceived); + application->_myTransmitter.processIncomingData(reinterpret_cast(incomingPacket.data()), + incomingPacket.size()); break; - case PACKET_TYPE_MIXED_AUDIO: + case PacketTypeMixedAudio: QMetaObject::invokeMethod(&application->_audio, "addReceivedAudioToBuffer", Qt::QueuedConnection, - Q_ARG(QByteArray, QByteArray((char*) incomingPacket, bytesReceived))); + Q_ARG(QByteArray, incomingPacket)); break; - case PACKET_TYPE_PARTICLE_ADD_RESPONSE: + case PacketTypeParticleAddResponse: // this will keep creatorTokenIDs to IDs mapped correctly - Particle::handleAddParticleResponse(incomingPacket, bytesReceived); + Particle::handleAddParticleResponse(incomingPacket); break; - case PACKET_TYPE_PARTICLE_DATA: - case PACKET_TYPE_PARTICLE_ERASE: - case PACKET_TYPE_VOXEL_DATA: - case PACKET_TYPE_VOXEL_ERASE: - case PACKET_TYPE_OCTREE_STATS: - case PACKET_TYPE_ENVIRONMENT_DATA: { + case PacketTypeParticleData: + case PacketTypeParticleErase: + case PacketTypeVoxelData: + case PacketTypeVoxelErase: + case PacketTypeOctreeStats: + case PacketTypeEnvironmentData: { PerformanceWarning warn(Menu::getInstance()->isOptionChecked(MenuOption::PipelineWarnings), "Application::networkReceive()... _voxelProcessor.queueReceivedPacket()"); bool wantExtraDebugging = application->getLogger()->extraDebugging(); - if (wantExtraDebugging && incomingPacket[0] == PACKET_TYPE_VOXEL_DATA) { + if (wantExtraDebugging && packetTypeForPacket(incomingPacket) == PacketTypeVoxelData) { int numBytesPacketHeader = numBytesForPacketHeader(incomingPacket); - unsigned char* dataAt = incomingPacket + numBytesPacketHeader; + unsigned char* dataAt = reinterpret_cast(incomingPacket.data()) + numBytesPacketHeader; dataAt += sizeof(VOXEL_PACKET_FLAGS); VOXEL_PACKET_SEQUENCE sequence = (*(VOXEL_PACKET_SEQUENCE*)dataAt); dataAt += sizeof(VOXEL_PACKET_SEQUENCE); @@ -80,50 +79,47 @@ void DatagramProcessor::processDatagrams() { VOXEL_PACKET_SENT_TIME arrivedAt = usecTimestampNow(); int flightTime = arrivedAt - sentAt; - printf("got PACKET_TYPE_VOXEL_DATA, sequence:%d flightTime:%d\n", sequence, flightTime); + printf("got PacketType_VOXEL_DATA, sequence:%d flightTime:%d\n", sequence, flightTime); } // add this packet to our list of voxel packets and process them on the voxel processing - application->_voxelProcessor.queueReceivedPacket(senderSockAddr, incomingPacket, bytesReceived); + application->_voxelProcessor.queueReceivedPacket(senderSockAddr, incomingPacket); break; } - case PACKET_TYPE_METAVOXEL_DATA: - application->_metavoxels.processData(QByteArray((const char*) incomingPacket, bytesReceived), - senderSockAddr); + case PacketTypeMetavoxelData: + application->_metavoxels.processData(incomingPacket, senderSockAddr); break; - case PACKET_TYPE_BULK_AVATAR_DATA: - case PACKET_TYPE_KILL_AVATAR: { + case PacketTypeBulkAvatarData: + case PacketTypeKillAvatar: { // update having heard from the avatar-mixer and record the bytes received SharedNodePointer avatarMixer = NodeList::getInstance()->nodeWithAddress(senderSockAddr); if (avatarMixer) { avatarMixer->setLastHeardMicrostamp(usecTimestampNow()); - avatarMixer->recordBytesReceived(bytesReceived); + avatarMixer->recordBytesReceived(incomingPacket.size()); - QByteArray datagram(reinterpret_cast(incomingPacket), bytesReceived); - - if (incomingPacket[0] == PACKET_TYPE_BULK_AVATAR_DATA) { + if (packetTypeForPacket(incomingPacket) == PacketTypeBulkAvatarData) { QMetaObject::invokeMethod(&application->getAvatarManager(), "processAvatarMixerDatagram", - Q_ARG(const QByteArray&, datagram), + Q_ARG(const QByteArray&, incomingPacket), Q_ARG(const QWeakPointer&, avatarMixer)); } else { // this is an avatar kill, pass it to the application AvatarManager QMetaObject::invokeMethod(&application->getAvatarManager(), "processKillAvatar", - Q_ARG(const QByteArray&, datagram)); + Q_ARG(const QByteArray&, incomingPacket)); } } - application->_bandwidthMeter.inputStream(BandwidthMeter::AVATARS).updateValue(bytesReceived); + application->_bandwidthMeter.inputStream(BandwidthMeter::AVATARS).updateValue(incomingPacket.size()); break; - } - case PACKET_TYPE_DATA_SERVER_GET: - case PACKET_TYPE_DATA_SERVER_PUT: - case PACKET_TYPE_DATA_SERVER_SEND: - case PACKET_TYPE_DATA_SERVER_CONFIRM: - DataServerClient::processMessageFromDataServer(incomingPacket, bytesReceived); + } + case PacketTypeDataServerGet: + case PacketTypeDataServerPut: + case PacketTypeDataServerSend: + case PacketTypeDataServerConfirm: + DataServerClient::processMessageFromDataServer(incomingPacket); break; default: - NodeList::getInstance()->processNodeData(senderSockAddr, incomingPacket, bytesReceived); + NodeList::getInstance()->processNodeData(senderSockAddr, incomingPacket); break; } } diff --git a/interface/src/Environment.cpp b/interface/src/Environment.cpp index 46c156f860..59f16fc5eb 100644 --- a/interface/src/Environment.cpp +++ b/interface/src/Environment.cpp @@ -148,32 +148,28 @@ bool Environment::findCapsulePenetration(const glm::vec3& start, const glm::vec3 return found; } -int Environment::parseData(const HifiSockAddr& senderAddress, unsigned char* sourceBuffer, int numBytes) { +int Environment::parseData(const HifiSockAddr& senderAddress, const QByteArray& packet) { // push past the packet header - unsigned char* start = sourceBuffer; - - int numBytesPacketHeader = numBytesForPacketHeader(sourceBuffer); - sourceBuffer += numBytesPacketHeader; - numBytes -= numBytesPacketHeader; + int bytesRead = numBytesForPacketHeader(packet); // get the lock for the duration of the call QMutexLocker locker(&_mutex); EnvironmentData newData; - while (numBytes > 0) { - int dataLength = newData.parseData(sourceBuffer, numBytes); + while (bytesRead < packet.size()) { + int dataLength = newData.parseData(reinterpret_cast(packet.data()) + bytesRead, + packet.size() - bytesRead); // update the mapping by address/ID _data[senderAddress][newData.getID()] = newData; - sourceBuffer += dataLength; - numBytes -= dataLength; + bytesRead += dataLength; } // remove the default mapping, if any _data.remove(HifiSockAddr()); - return sourceBuffer - start; + return bytesRead; } ProgramObject* Environment::createSkyProgram(const char* from, int* locations) { diff --git a/interface/src/Environment.h b/interface/src/Environment.h index fc572c5e03..273ee54cee 100644 --- a/interface/src/Environment.h +++ b/interface/src/Environment.h @@ -34,7 +34,7 @@ public: bool findCapsulePenetration(const glm::vec3& start, const glm::vec3& end, float radius, glm::vec3& penetration); - int parseData(const HifiSockAddr& senderSockAddr, unsigned char* sourceBuffer, int numBytes); + int parseData(const HifiSockAddr& senderSockAddr, const QByteArray& packet); private: diff --git a/interface/src/MetavoxelSystem.cpp b/interface/src/MetavoxelSystem.cpp index 258db6da00..5bd83d969c 100644 --- a/interface/src/MetavoxelSystem.cpp +++ b/interface/src/MetavoxelSystem.cpp @@ -167,8 +167,7 @@ bool MetavoxelSystem::PointVisitor::visit(MetavoxelInfo& info) { } static QByteArray createDatagramHeader(const QUuid& sessionID) { - QByteArray header(MAX_PACKET_HEADER_BYTES, 0); - populateTypeAndVersion(reinterpret_cast(header.data()), PACKET_TYPE_METAVOXEL_DATA); + QByteArray header = byteArrayWithPopluatedHeader(PacketTypeMetavoxelData); header += sessionID.toRfc4122(); return header; } diff --git a/interface/src/ParticleTreeRenderer.h b/interface/src/ParticleTreeRenderer.h index 1c76cf623d..20cb41b207 100644 --- a/interface/src/ParticleTreeRenderer.h +++ b/interface/src/ParticleTreeRenderer.h @@ -29,8 +29,8 @@ public: virtual Octree* createTree() { return new ParticleTree(true); } virtual NODE_TYPE getMyNodeType() const { return NODE_TYPE_PARTICLE_SERVER; } - virtual PACKET_TYPE getMyQueryMessageType() const { return PACKET_TYPE_PARTICLE_QUERY; } - virtual PACKET_TYPE getExpectedPacketType() const { return PACKET_TYPE_PARTICLE_DATA; } + virtual PacketType getMyQueryMessageType() const { return PacketTypeParticleQuery; } + virtual PacketType getExpectedPacketType() const { return PacketTypeParticleData; } virtual void renderElement(OctreeElement* element, RenderArgs* args); void update(); diff --git a/interface/src/VoxelPacketProcessor.cpp b/interface/src/VoxelPacketProcessor.cpp index 6f51dc041d..bdb934430c 100644 --- a/interface/src/VoxelPacketProcessor.cpp +++ b/interface/src/VoxelPacketProcessor.cpp @@ -14,16 +14,18 @@ #include "Menu.h" #include "VoxelPacketProcessor.h" -void VoxelPacketProcessor::processPacket(const HifiSockAddr& senderSockAddr, unsigned char* packetData, ssize_t packetLength) { +void VoxelPacketProcessor::processPacket(const HifiSockAddr& senderSockAddr, const QByteArray& packet) { PerformanceWarning warn(Menu::getInstance()->isOptionChecked(MenuOption::PipelineWarnings), "VoxelPacketProcessor::processPacket()"); + + QByteArray mutablePacket = packet; const int WAY_BEHIND = 300; if (packetsToProcessCount() > WAY_BEHIND && Application::getInstance()->getLogger()->extraDebugging()) { qDebug("VoxelPacketProcessor::processPacket() packets to process=%d", packetsToProcessCount()); } - ssize_t messageLength = packetLength; + ssize_t messageLength = mutablePacket.size(); Application* app = Application::getInstance(); bool wasStatsPacket = false; @@ -34,18 +36,19 @@ void VoxelPacketProcessor::processPacket(const HifiSockAddr& senderSockAddr, uns app->_voxels.killLocalVoxels(); app->_wantToKillLocalVoxels = false; } + + PacketType voxelPacketType = packetTypeForPacket(mutablePacket); - // note: PACKET_TYPE_OCTREE_STATS can have PACKET_TYPE_VOXEL_DATA - // immediately following them inside the same packet. So, we process the PACKET_TYPE_OCTREE_STATS first + // note: PacketType_OCTREE_STATS can have PacketType_VOXEL_DATA + // immediately following them inside the same packet. So, we process the PacketType_OCTREE_STATS first // then process any remaining bytes as if it was another packet - if (packetData[0] == PACKET_TYPE_OCTREE_STATS) { + if (voxelPacketType == PacketTypeOctreeStats) { - int statsMessageLength = app->parseOctreeStats(packetData, messageLength, senderSockAddr); + int statsMessageLength = app->parseOctreeStats(mutablePacket, senderSockAddr); wasStatsPacket = true; if (messageLength > statsMessageLength) { - packetData += statsMessageLength; - messageLength -= statsMessageLength; - if (!packetVersionMatch(packetData, senderSockAddr)) { + mutablePacket = mutablePacket.mid(statsMessageLength); + if (!packetVersionMatch(packet)) { return; // bail since piggyback data doesn't match our versioning } } else { @@ -53,31 +56,31 @@ void VoxelPacketProcessor::processPacket(const HifiSockAddr& senderSockAddr, uns return; // bail since no piggyback data } } // fall through to piggyback message - + + voxelPacketType = packetTypeForPacket(mutablePacket); + if (Menu::getInstance()->isOptionChecked(MenuOption::Voxels)) { - app->trackIncomingVoxelPacket(packetData, messageLength, senderSockAddr, wasStatsPacket); + app->trackIncomingVoxelPacket(mutablePacket, senderSockAddr, wasStatsPacket); SharedNodePointer serverNode = NodeList::getInstance()->nodeWithAddress(senderSockAddr); if (serverNode && serverNode->getActiveSocket() && *serverNode->getActiveSocket() == senderSockAddr) { - switch(packetData[0]) { - case PACKET_TYPE_PARTICLE_ERASE: { - app->_particles.processEraseMessage(QByteArray((char*) packetData, messageLength), - senderSockAddr, serverNode.data()); + switch(voxelPacketType) { + case PacketTypeParticleErase: { + app->_particles.processEraseMessage(mutablePacket, senderSockAddr, serverNode.data()); } break; - case PACKET_TYPE_PARTICLE_DATA: { - app->_particles.processDatagram(QByteArray((char*) packetData, messageLength), - senderSockAddr, serverNode.data()); + case PacketTypeParticleData: { + app->_particles.processDatagram(mutablePacket, senderSockAddr, serverNode.data()); } break; - case PACKET_TYPE_ENVIRONMENT_DATA: { - app->_environment.parseData(senderSockAddr, packetData, messageLength); + case PacketTypeEnvironmentData: { + app->_environment.parseData(senderSockAddr, mutablePacket); } break; default : { app->_voxels.setDataSourceUUID(serverNode->getUUID()); - app->_voxels.parseData(packetData, messageLength); + app->_voxels.parseData(mutablePacket); app->_voxels.setDataSourceUUID(QUuid()); } break; } diff --git a/interface/src/VoxelPacketProcessor.h b/interface/src/VoxelPacketProcessor.h index e8e77e6895..e0c3e9f542 100644 --- a/interface/src/VoxelPacketProcessor.h +++ b/interface/src/VoxelPacketProcessor.h @@ -17,6 +17,6 @@ /// the user is responsible for reading inbound packets and adding them to the processing queue by calling queueReceivedPacket() class VoxelPacketProcessor : public ReceivedPacketProcessor { protected: - virtual void processPacket(const HifiSockAddr& senderSockAddr, unsigned char* packetData, ssize_t packetLength); + virtual void processPacket(const HifiSockAddr& senderSockAddr, const QByteArray& packet); }; #endif // __shared__VoxelPacketProcessor__ diff --git a/interface/src/VoxelSystem.cpp b/interface/src/VoxelSystem.cpp index c5071570d5..029690e56a 100644 --- a/interface/src/VoxelSystem.cpp +++ b/interface/src/VoxelSystem.cpp @@ -16,7 +16,6 @@ #include #include #include -#include #include "Application.h" #include "CoverageMap.h" @@ -550,17 +549,17 @@ bool VoxelSystem::readFromSchematicFile(const char* filename) { return result; } -int VoxelSystem::parseData(unsigned char* sourceBuffer, int numBytes) { +int VoxelSystem::parseData(const QByteArray& packet) { bool showTimingDetails = Menu::getInstance()->isOptionChecked(MenuOption::PipelineWarnings); PerformanceWarning warn(showTimingDetails, "VoxelSystem::parseData()",showTimingDetails); - unsigned char command = *sourceBuffer; - int numBytesPacketHeader = numBytesForPacketHeader(sourceBuffer); + PacketType command = packetTypeForPacket(packet); + int numBytesPacketHeader = numBytesForPacketHeader(packet); switch(command) { - case PACKET_TYPE_VOXEL_DATA: { - PerformanceWarning warn(showTimingDetails, "VoxelSystem::parseData() PACKET_TYPE_VOXEL_DATA part...",showTimingDetails); - - unsigned char* dataAt = sourceBuffer + numBytesPacketHeader; + case PacketTypeVoxelData: { + PerformanceWarning warn(showTimingDetails, "VoxelSystem::parseData() PacketType_VOXEL_DATA part...",showTimingDetails); + + const unsigned char* dataAt = reinterpret_cast(packet.data()) + numBytesPacketHeader; VOXEL_PACKET_FLAGS flags = (*(VOXEL_PACKET_FLAGS*)(dataAt)); dataAt += sizeof(VOXEL_PACKET_FLAGS); @@ -577,7 +576,7 @@ int VoxelSystem::parseData(unsigned char* sourceBuffer, int numBytes) { int flightTime = arrivedAt - sentAt; VOXEL_PACKET_INTERNAL_SECTION_SIZE sectionLength = 0; - int dataBytes = numBytes - VOXEL_PACKET_HEADER_SIZE; + int dataBytes = packet.size() - VOXEL_PACKET_HEADER_SIZE; int subsection = 1; while (dataBytes > 0) { @@ -605,7 +604,8 @@ int VoxelSystem::parseData(unsigned char* sourceBuffer, int numBytes) { " color:%s compressed:%s sequence: %u flight:%d usec size:%d data:%d" " subsection:%d sectionLength:%d uncompressed:%d", debug::valueOf(packetIsColored), debug::valueOf(packetIsCompressed), - sequence, flightTime, numBytes, dataBytes, subsection, sectionLength, packetData.getUncompressedSize()); + sequence, flightTime, packet.size(), dataBytes, subsection, sectionLength, + packetData.getUncompressedSize()); } _tree->readBitstreamToTree(packetData.getUncompressedData(), packetData.getUncompressedSize(), args); unlockTree(); @@ -616,7 +616,8 @@ int VoxelSystem::parseData(unsigned char* sourceBuffer, int numBytes) { } subsection++; } - break; + default: + break; } if (!_useFastVoxelPipeline || _writeRenderFullVBO) { setupNewVoxelsForDrawing(); @@ -624,9 +625,9 @@ int VoxelSystem::parseData(unsigned char* sourceBuffer, int numBytes) { setupNewVoxelsForDrawingSingleNode(DONT_BAIL_EARLY); } - Application::getInstance()->getBandwidthMeter()->inputStream(BandwidthMeter::VOXELS).updateValue(numBytes); + Application::getInstance()->getBandwidthMeter()->inputStream(BandwidthMeter::VOXELS).updateValue(packet.size()); - return numBytes; + return packet.size(); } void VoxelSystem::setupNewVoxelsForDrawing() { diff --git a/interface/src/VoxelSystem.h b/interface/src/VoxelSystem.h index 728106a922..915b5a05b4 100644 --- a/interface/src/VoxelSystem.h +++ b/interface/src/VoxelSystem.h @@ -49,7 +49,7 @@ public: void setDataSourceUUID(const QUuid& dataSourceUUID) { _dataSourceUUID = dataSourceUUID; } const QUuid& getDataSourceUUID() const { return _dataSourceUUID; } - int parseData(unsigned char* sourceBuffer, int numBytes); + int parseData(const QByteArray& packet); virtual void init(); void simulate(float deltaTime) { } diff --git a/interface/src/avatar/Avatar.cpp b/interface/src/avatar/Avatar.cpp index 5e41619997..61d2ddb8a0 100644 --- a/interface/src/avatar/Avatar.cpp +++ b/interface/src/avatar/Avatar.cpp @@ -12,7 +12,6 @@ #include #include -#include #include #include @@ -336,11 +335,11 @@ bool Avatar::findSphereCollision(const glm::vec3& sphereCenter, float sphereRadi return false; } -int Avatar::parseData(unsigned char* sourceBuffer, int numBytes) { +int Avatar::parseData(const QByteArray& packet) { // change in position implies movement glm::vec3 oldPosition = _position; - int bytesRead = AvatarData::parseData(sourceBuffer, numBytes); + int bytesRead = AvatarData::parseData(packet); const float MOVE_DISTANCE_THRESHOLD = 0.001f; _moving = glm::distance(oldPosition, _position) > MOVE_DISTANCE_THRESHOLD; diff --git a/interface/src/avatar/Avatar.h b/interface/src/avatar/Avatar.h index 10a3760f6e..b8f27a0edf 100755 --- a/interface/src/avatar/Avatar.h +++ b/interface/src/avatar/Avatar.h @@ -114,7 +114,7 @@ public: virtual bool isMyAvatar() { return false; } - int parseData(unsigned char* sourceBuffer, int numBytes); + int parseData(const QByteArray& packet); static void renderJointConnectingCone(glm::vec3 position1, glm::vec3 position2, float radius1, float radius2); diff --git a/interface/src/avatar/AvatarManager.cpp b/interface/src/avatar/AvatarManager.cpp index dd1686a0d2..8228ec9e64 100644 --- a/interface/src/avatar/AvatarManager.cpp +++ b/interface/src/avatar/AvatarManager.cpp @@ -164,15 +164,11 @@ void AvatarManager::processDataServerResponse(const QString& userString, const Q } void AvatarManager::processAvatarMixerDatagram(const QByteArray& datagram, const QWeakPointer& mixerWeakPointer) { - unsigned char packetData[MAX_PACKET_SIZE]; - memcpy(packetData, datagram.data(), datagram.size()); - int numBytesPacketHeader = numBytesForPacketHeader(packetData); + int bytesRead = numBytesForPacketHeader(datagram); - int bytesRead = numBytesPacketHeader; - - unsigned char avatarData[MAX_PACKET_SIZE]; - int numBytesDummyPacketHeader = populateTypeAndVersion(avatarData, PACKET_TYPE_HEAD_DATA); + QByteArray dummyAvatarByteArray = byteArrayWithPopluatedHeader(PacketTypeAvatarData); + int numDummyByteArrayHeaderBytes = dummyAvatarByteArray.size(); // enumerate over all of the avatars in this packet // only add them if mixerWeakPointer points to something (meaning that mixer is still around) @@ -197,18 +193,17 @@ void AvatarManager::processAvatarMixerDatagram(const QByteArray& datagram, const } // copy the rest of the packet to the avatarData holder so we can read the next Avatar from there - memcpy(avatarData + numBytesDummyPacketHeader, packetData + bytesRead, datagram.size() - bytesRead); + dummyAvatarByteArray.resize(numDummyByteArrayHeaderBytes); + dummyAvatarByteArray += datagram.mid(bytesRead); // have the matching (or new) avatar parse the data from the packet - bytesRead += matchingAvatar->parseData(avatarData, datagram.size() - bytesRead); + bytesRead += matchingAvatar->parseData(dummyAvatarByteArray); } } void AvatarManager::processKillAvatar(const QByteArray& datagram) { // read the node id - QUuid nodeUUID = QUuid::fromRfc4122(datagram.mid(numBytesForPacketHeader(reinterpret_cast - (datagram.data())), - NUM_BYTES_RFC4122_UUID)); + QUuid nodeUUID = QUuid::fromRfc4122(datagram.mid(numBytesForPacketHeader(datagram), NUM_BYTES_RFC4122_UUID)); // remove the avatar with that UUID from our hash, if it exists AvatarHash::iterator matchedAvatar = _avatarHash.find(nodeUUID); diff --git a/interface/src/avatar/MyAvatar.cpp b/interface/src/avatar/MyAvatar.cpp index ca7a3b863b..cee524c171 100644 --- a/interface/src/avatar/MyAvatar.cpp +++ b/interface/src/avatar/MyAvatar.cpp @@ -12,7 +12,6 @@ #include #include -#include #include #include @@ -473,18 +472,8 @@ void MyAvatar::loadData(QSettings* settings) { } void MyAvatar::sendKillAvatar() { - unsigned char packet[MAX_PACKET_SIZE]; - unsigned char* packetPosition = packet; - - packetPosition += populateTypeAndVersion(packetPosition, PACKET_TYPE_KILL_AVATAR); - - NodeList* nodeList = NodeList::getInstance(); - - QByteArray rfcUUID = nodeList->getOwnerUUID().toRfc4122(); - memcpy(packetPosition, rfcUUID.constData(), rfcUUID.size()); - packetPosition += rfcUUID.size(); - - nodeList->broadcastToNodes(packet, packetPosition - packet, QSet() << NODE_TYPE_AVATAR_MIXER); + QByteArray killPacket = byteArrayWithPopluatedHeader(PacketTypeKillAvatar); + NodeList::getInstance()->broadcastToNodes(killPacket, QSet() << NODE_TYPE_AVATAR_MIXER); } void MyAvatar::orbit(const glm::vec3& position, int deltaX, int deltaY) { diff --git a/interface/src/devices/Transmitter.cpp b/interface/src/devices/Transmitter.cpp index 8ae6bdc405..e6da39447c 100644 --- a/interface/src/devices/Transmitter.cpp +++ b/interface/src/devices/Transmitter.cpp @@ -60,7 +60,7 @@ void Transmitter::resetLevels() { void Transmitter::processIncomingData(unsigned char* packetData, int numBytes) { // Packet's first byte is 'T' - int numBytesPacketHeader = numBytesForPacketHeader(packetData); + int numBytesPacketHeader = numBytesForPacketHeader(reinterpret_cast(packetData)); const int ROTATION_MARKER_SIZE = 1; // 'R' = Rotation (clockwise about x,y,z) const int ACCELERATION_MARKER_SIZE = 1; // 'A' = Acceleration (x,y,z) diff --git a/libraries/audio/src/AudioInjector.cpp b/libraries/audio/src/AudioInjector.cpp index 60ff777452..fd8bdc1a89 100644 --- a/libraries/audio/src/AudioInjector.cpp +++ b/libraries/audio/src/AudioInjector.cpp @@ -45,45 +45,28 @@ void AudioInjector::injectAudio() { NodeList* nodeList = NodeList::getInstance(); // setup the packet for injected audio - unsigned char injectedAudioPacket[MAX_PACKET_SIZE]; - unsigned char* currentPacketPosition = injectedAudioPacket; + QByteArray injectAudioPacket = byteArrayWithPopluatedHeader(PacketTypeInjectAudio); + QDataStream packetStream(&injectAudioPacket, QIODevice::Append); - int numBytesPacketHeader = populateTypeAndVersion(injectedAudioPacket, PACKET_TYPE_INJECT_AUDIO); - currentPacketPosition += numBytesPacketHeader; - - // pack the session UUID for this Node - QByteArray rfcSessionUUID = NodeList::getInstance()->getOwnerUUID().toRfc4122(); - memcpy(currentPacketPosition, rfcSessionUUID.constData(), rfcSessionUUID.size()); - currentPacketPosition += rfcSessionUUID.size(); - - // pick a random UUID to use for this stream - QUuid randomStreamUUID = QUuid::createUuid(); - QByteArray rfcStreamUUID = randomStreamUUID.toRfc4122(); - memcpy(currentPacketPosition, rfcStreamUUID, rfcStreamUUID.size()); - currentPacketPosition += rfcStreamUUID.size(); + packetStream << QUuid::createUuid(); // pack the flag for loopback - bool loopbackFlag = (_options.getLoopbackAudioInterface() == NULL); - memcpy(currentPacketPosition, &loopbackFlag, sizeof(loopbackFlag)); - currentPacketPosition += sizeof(loopbackFlag); + uchar loopbackFlag = (uchar) (_options.getLoopbackAudioInterface() == NULL); + packetStream << loopbackFlag; // pack the position for injected audio - memcpy(currentPacketPosition, &_options.getPosition(), sizeof(_options.getPosition())); - currentPacketPosition += sizeof(_options.getPosition()); + packetStream.writeRawData(reinterpret_cast(&_options.getPosition()), sizeof(_options.getPosition())); // pack our orientation for injected audio - memcpy(currentPacketPosition, &_options.getOrientation(), sizeof(_options.getOrientation())); - currentPacketPosition += sizeof(_options.getOrientation()); + packetStream.writeRawData(reinterpret_cast(&_options.getOrientation()), sizeof(_options.getOrientation())); // pack zero for radius float radius = 0; - memcpy(currentPacketPosition, &radius, sizeof(radius)); - currentPacketPosition += sizeof(radius); + packetStream << radius; // pack 255 for attenuation byte - uchar volume = MAX_INJECTOR_VOLUME * _options.getVolume(); - memcpy(currentPacketPosition, &volume, sizeof(volume)); - currentPacketPosition += sizeof(volume); + quint8 volume = MAX_INJECTOR_VOLUME * _options.getVolume(); + packetStream << volume; timeval startTime = {}; gettimeofday(&startTime, NULL); @@ -91,24 +74,26 @@ void AudioInjector::injectAudio() { int currentSendPosition = 0; + int numPreAudioDataBytes = injectAudioPacket.size(); + // loop to send off our audio in NETWORK_BUFFER_LENGTH_SAMPLES_PER_CHANNEL byte chunks while (currentSendPosition < soundByteArray.size()) { int bytesToCopy = std::min(NETWORK_BUFFER_LENGTH_BYTES_PER_CHANNEL, soundByteArray.size() - currentSendPosition); - // copy the next NETWORK_BUFFER_LENGTH_BYTES_PER_CHANNEL bytes to the packet - memcpy(currentPacketPosition, soundByteArray.data() + currentSendPosition, - bytesToCopy); + // resize the QByteArray to the right size + injectAudioPacket.resize(numPreAudioDataBytes + bytesToCopy); + // copy the next NETWORK_BUFFER_LENGTH_BYTES_PER_CHANNEL bytes to the packet + memcpy(injectAudioPacket.data() + numPreAudioDataBytes, soundByteArray.data() + currentSendPosition, bytesToCopy); // grab our audio mixer from the NodeList, if it exists SharedNodePointer audioMixer = nodeList->soloNodeOfType(NODE_TYPE_AUDIO_MIXER); if (audioMixer && nodeList->getNodeActiveSocketOrPing(audioMixer.data())) { // send off this audio packet - nodeList->getNodeSocket().writeDatagram((char*) injectedAudioPacket, - (currentPacketPosition - injectedAudioPacket) + bytesToCopy, + nodeList->getNodeSocket().writeDatagram(injectAudioPacket, audioMixer->getActiveSocket()->getAddress(), audioMixer->getActiveSocket()->getPort()); } diff --git a/libraries/audio/src/AudioRingBuffer.cpp b/libraries/audio/src/AudioRingBuffer.cpp index e65d4632f6..8a444e50fd 100644 --- a/libraries/audio/src/AudioRingBuffer.cpp +++ b/libraries/audio/src/AudioRingBuffer.cpp @@ -50,9 +50,9 @@ void AudioRingBuffer::resizeForFrameSize(qint64 numFrameSamples) { _endOfLastWrite = _buffer; } -int AudioRingBuffer::parseData(unsigned char* sourceBuffer, int numBytes) { - int numBytesPacketHeader = numBytesForPacketHeader(sourceBuffer); - return writeData((char*) sourceBuffer + numBytesPacketHeader, numBytes - numBytesPacketHeader); +int AudioRingBuffer::parseData(const QByteArray& packet) { + int numBytesPacketHeader = numBytesForPacketHeader(packet); + return writeData(packet.data() + numBytesPacketHeader, packet.size() - numBytesPacketHeader); } qint64 AudioRingBuffer::readSamples(int16_t* destination, qint64 maxSamples) { diff --git a/libraries/audio/src/AudioRingBuffer.h b/libraries/audio/src/AudioRingBuffer.h index 0bcd127a2e..b6e75a2e86 100644 --- a/libraries/audio/src/AudioRingBuffer.h +++ b/libraries/audio/src/AudioRingBuffer.h @@ -44,7 +44,7 @@ public: int getSampleCapacity() const { return _sampleCapacity; } - int parseData(unsigned char* sourceBuffer, int numBytes); + int parseData(const QByteArray& packet); qint64 readSamples(int16_t* destination, qint64 maxSamples); qint64 writeSamples(const int16_t* source, qint64 maxSamples); diff --git a/libraries/audio/src/InjectedAudioRingBuffer.cpp b/libraries/audio/src/InjectedAudioRingBuffer.cpp index ae8574f3c9..d7b40f63ea 100644 --- a/libraries/audio/src/InjectedAudioRingBuffer.cpp +++ b/libraries/audio/src/InjectedAudioRingBuffer.cpp @@ -26,29 +26,31 @@ InjectedAudioRingBuffer::InjectedAudioRingBuffer(const QUuid& streamIdentifier) const uchar MAX_INJECTOR_VOLUME = 255; -int InjectedAudioRingBuffer::parseData(unsigned char* sourceBuffer, int numBytes) { - unsigned char* currentBuffer = sourceBuffer + numBytesForPacketHeader(sourceBuffer); +int InjectedAudioRingBuffer::parseData(const QByteArray& packet) { + // setup a data stream to read from this packet + QDataStream packetStream(packet); + packetStream.skipRawData(numBytesForPacketHeader(packet)); - // push past the UUID for this node and the stream identifier - currentBuffer += (NUM_BYTES_RFC4122_UUID * 2); + // push past the stream identifier + packetStream.skipRawData(NUM_BYTES_RFC4122_UUID); // pull the loopback flag and set our boolean uchar shouldLoopback; - memcpy(&shouldLoopback, currentBuffer, sizeof(shouldLoopback)); - currentBuffer += sizeof(shouldLoopback); + packetStream >> shouldLoopback; _shouldLoopbackForNode = (shouldLoopback == 1); // use parsePositionalData in parent PostionalAudioRingBuffer class to pull common positional data - currentBuffer += parsePositionalData(currentBuffer, numBytes - (currentBuffer - sourceBuffer)); + packetStream.skipRawData(parsePositionalData(packet.mid(packetStream.device()->pos()))); // pull out the radius for this injected source - if it's zero this is a point source - memcpy(&_radius, currentBuffer, sizeof(_radius)); - currentBuffer += sizeof(_radius); + packetStream >> _radius; - unsigned int attenuationByte = *(currentBuffer++); + quint8 attenuationByte = 0; + packetStream >> attenuationByte; _attenuationRatio = attenuationByte / (float) MAX_INJECTOR_VOLUME; - currentBuffer += writeData((char*) currentBuffer, numBytes - (currentBuffer - sourceBuffer)); + packetStream.skipRawData(writeData(packet.data() + packetStream.device()->pos(), + packet.size() - packetStream.device()->pos())); - return currentBuffer - sourceBuffer; + return packetStream.device()->pos(); } diff --git a/libraries/audio/src/InjectedAudioRingBuffer.h b/libraries/audio/src/InjectedAudioRingBuffer.h index b5845366fb..d4dfb5e360 100644 --- a/libraries/audio/src/InjectedAudioRingBuffer.h +++ b/libraries/audio/src/InjectedAudioRingBuffer.h @@ -17,7 +17,7 @@ class InjectedAudioRingBuffer : public PositionalAudioRingBuffer { public: InjectedAudioRingBuffer(const QUuid& streamIdentifier = QUuid()); - int parseData(unsigned char* sourceBuffer, int numBytes); + int parseData(const QByteArray& packet); const QUuid& getStreamIdentifier() const { return _streamIdentifier; } float getRadius() const { return _radius; } diff --git a/libraries/audio/src/PositionalAudioRingBuffer.cpp b/libraries/audio/src/PositionalAudioRingBuffer.cpp index 97793a98fb..fa515a5bf7 100644 --- a/libraries/audio/src/PositionalAudioRingBuffer.cpp +++ b/libraries/audio/src/PositionalAudioRingBuffer.cpp @@ -35,23 +35,24 @@ PositionalAudioRingBuffer::PositionalAudioRingBuffer(PositionalAudioRingBuffer:: PositionalAudioRingBuffer::~PositionalAudioRingBuffer() { } -int PositionalAudioRingBuffer::parseData(unsigned char* sourceBuffer, int numBytes) { - unsigned char* currentBuffer = sourceBuffer + numBytesForPacketHeader(sourceBuffer); - currentBuffer += NUM_BYTES_RFC4122_UUID; // the source UUID - currentBuffer += parsePositionalData(currentBuffer, numBytes - (currentBuffer - sourceBuffer)); - currentBuffer += writeData((char*) currentBuffer, numBytes - (currentBuffer - sourceBuffer)); +int PositionalAudioRingBuffer::parseData(const QByteArray& packet) { + QDataStream packetStream(packet); + + // skip the source UUID + packetStream.skipRawData(NUM_BYTES_RFC4122_UUID); + + packetStream.skipRawData(parsePositionalData(packet.mid(packetStream.device()->pos()))); + packetStream.skipRawData(writeData(packet.data() + packetStream.device()->pos(), + packet.size() - packetStream.device()->pos())); - return currentBuffer - sourceBuffer; + return packetStream.device()->pos(); } -int PositionalAudioRingBuffer::parsePositionalData(unsigned char* sourceBuffer, int numBytes) { - unsigned char* currentBuffer = sourceBuffer; - - memcpy(&_position, currentBuffer, sizeof(_position)); - currentBuffer += sizeof(_position); - - memcpy(&_orientation, currentBuffer, sizeof(_orientation)); - currentBuffer += sizeof(_orientation); +int PositionalAudioRingBuffer::parsePositionalData(const QByteArray& positionalByteArray) { + QDataStream packetStream(positionalByteArray); + + packetStream.readRawData(reinterpret_cast(&_position), sizeof(_position)); + packetStream.readRawData(reinterpret_cast(&_orientation), sizeof(_orientation)); // if this node sent us a NaN for first float in orientation then don't consider this good audio and bail if (isnan(_orientation.x)) { @@ -59,7 +60,7 @@ int PositionalAudioRingBuffer::parsePositionalData(unsigned char* sourceBuffer, return 0; } - return currentBuffer - sourceBuffer; + return packetStream.device()->pos(); } bool PositionalAudioRingBuffer::shouldBeAddedToMix(int numJitterBufferSamples) { diff --git a/libraries/audio/src/PositionalAudioRingBuffer.h b/libraries/audio/src/PositionalAudioRingBuffer.h index 55ed627c4d..e3fffa1689 100644 --- a/libraries/audio/src/PositionalAudioRingBuffer.h +++ b/libraries/audio/src/PositionalAudioRingBuffer.h @@ -24,9 +24,9 @@ public: PositionalAudioRingBuffer(PositionalAudioRingBuffer::Type type); ~PositionalAudioRingBuffer(); - int parseData(unsigned char* sourceBuffer, int numBytes); - int parsePositionalData(unsigned char* sourceBuffer, int numBytes); - int parseListenModeData(unsigned char* sourceBuffer, int numBytes); + int parseData(const QByteArray& packet); + int parsePositionalData(const QByteArray& positionalByteArray); + int parseListenModeData(const QByteArray& listenModeByteArray); bool shouldBeAddedToMix(int numJitterBufferSamples); diff --git a/libraries/avatars/src/AvatarData.cpp b/libraries/avatars/src/AvatarData.cpp index 8f548869ec..f52af7cff8 100644 --- a/libraries/avatars/src/AvatarData.cpp +++ b/libraries/avatars/src/AvatarData.cpp @@ -52,9 +52,7 @@ void AvatarData::setHandPosition(const glm::vec3& handPosition) { _handPosition = glm::inverse(getOrientation()) * (handPosition - _position); } -int AvatarData::getBroadcastData(unsigned char* destinationBuffer) { - unsigned char* bufferStart = destinationBuffer; - +QByteArray AvatarData::toByteArray() { // TODO: DRY this up to a shared method // that can pack any type given the number of bytes // and return the number of bytes to push the pointer @@ -68,9 +66,14 @@ int AvatarData::getBroadcastData(unsigned char* destinationBuffer) { _handData = new HandData(this); } - // Body world position - memcpy(destinationBuffer, &_position, sizeof(float) * 3); - destinationBuffer += sizeof(float) * 3; + QByteArray avatarDataByteArray; + avatarDataByteArray.resize(MAX_PACKET_SIZE); + + unsigned char* destinationBuffer = reinterpret_cast(avatarDataByteArray.data()); + unsigned char* startPosition = destinationBuffer; + + memcpy(destinationBuffer, &_position, sizeof(_position)); + destinationBuffer += sizeof(_position); // Body rotation (NOTE: This needs to become a quaternion to save two bytes) destinationBuffer += packFloatAngleToTwoByte(destinationBuffer, _bodyYaw); @@ -85,6 +88,7 @@ int AvatarData::getBroadcastData(unsigned char* destinationBuffer) { destinationBuffer += packFloatAngleToTwoByte(destinationBuffer, _headData->_pitch); destinationBuffer += packFloatAngleToTwoByte(destinationBuffer, _headData->_roll); + // Head lean X,Z (head lateral and fwd/back motion relative to torso) memcpy(destinationBuffer, &_headData->_leanSideways, sizeof(_headData->_leanSideways)); destinationBuffer += sizeof(_headData->_leanSideways); @@ -150,11 +154,11 @@ int AvatarData::getBroadcastData(unsigned char* destinationBuffer) { // leap hand data destinationBuffer += _handData->encodeRemoteData(destinationBuffer); - return destinationBuffer - bufferStart; + return avatarDataByteArray.left(destinationBuffer - startPosition); } // called on the other nodes - assigns it to my views of the others -int AvatarData::parseData(unsigned char* sourceBuffer, int numBytes) { +int AvatarData::parseData(const QByteArray& packet) { // lazily allocate memory for HeadData in case we're not an Avatar instance if (!_headData) { @@ -166,67 +170,68 @@ int AvatarData::parseData(unsigned char* sourceBuffer, int numBytes) { _handData = new HandData(this); } - // increment to push past the packet header - int numBytesPacketHeader = numBytesForPacketHeader(sourceBuffer); - sourceBuffer += numBytesPacketHeader; + QDataStream packetStream(packet); + packetStream.skipRawData(numBytesForPacketHeader(packet)); - unsigned char* startPosition = sourceBuffer; - - // push past the node session UUID - sourceBuffer += NUM_BYTES_RFC4122_UUID; - - // Body world position - memcpy(&_position, sourceBuffer, sizeof(float) * 3); - sourceBuffer += sizeof(float) * 3; + packetStream.readRawData(reinterpret_cast(&_position), sizeof(_position)); // Body rotation (NOTE: This needs to become a quaternion to save two bytes) - sourceBuffer += unpackFloatAngleFromTwoByte((uint16_t*) sourceBuffer, &_bodyYaw); - sourceBuffer += unpackFloatAngleFromTwoByte((uint16_t*) sourceBuffer, &_bodyPitch); - sourceBuffer += unpackFloatAngleFromTwoByte((uint16_t*) sourceBuffer, &_bodyRoll); - - // Body scale - sourceBuffer += unpackFloatRatioFromTwoByte(sourceBuffer, _targetScale); + uint16_t twoByteHolder; + packetStream >> twoByteHolder; + unpackFloatAngleFromTwoByte(&twoByteHolder, &_bodyYaw); + + packetStream >> twoByteHolder; + unpackFloatAngleFromTwoByte(&twoByteHolder, &_bodyPitch); + + packetStream >> twoByteHolder; + unpackFloatAngleFromTwoByte(&twoByteHolder, &_bodyRoll); + + // body scale + packetStream >> twoByteHolder; + unpackFloatRatioFromTwoByte(reinterpret_cast(&twoByteHolder), _targetScale); // Head rotation (NOTE: This needs to become a quaternion to save two bytes) float headYaw, headPitch, headRoll; - sourceBuffer += unpackFloatAngleFromTwoByte((uint16_t*) sourceBuffer, &headYaw); - sourceBuffer += unpackFloatAngleFromTwoByte((uint16_t*) sourceBuffer, &headPitch); - sourceBuffer += unpackFloatAngleFromTwoByte((uint16_t*) sourceBuffer, &headRoll); + + packetStream >> twoByteHolder; + unpackFloatAngleFromTwoByte(&twoByteHolder, &headYaw); + + packetStream >> twoByteHolder; + unpackFloatAngleFromTwoByte(&twoByteHolder, &headPitch); + + packetStream >> twoByteHolder; + unpackFloatAngleFromTwoByte(&twoByteHolder, &headRoll); _headData->setYaw(headYaw); _headData->setPitch(headPitch); _headData->setRoll(headRoll); // Head position relative to pelvis - memcpy(&_headData->_leanSideways, sourceBuffer, sizeof(_headData->_leanSideways)); - sourceBuffer += sizeof(float); - memcpy(&_headData->_leanForward, sourceBuffer, sizeof(_headData->_leanForward)); - sourceBuffer += sizeof(_headData->_leanForward); + packetStream >> _headData->_leanSideways; + packetStream >> _headData->_leanForward; // Hand Position - is relative to body position glm::vec3 handPositionRelative; - memcpy(&handPositionRelative, sourceBuffer, sizeof(float) * 3); + packetStream.readRawData(reinterpret_cast(&handPositionRelative), sizeof(handPositionRelative)); _handPosition = _position + handPositionRelative; - sourceBuffer += sizeof(float) * 3; - - // Lookat Position - memcpy(&_headData->_lookAtPosition, sourceBuffer, sizeof(_headData->_lookAtPosition)); - sourceBuffer += sizeof(_headData->_lookAtPosition); + + packetStream.readRawData(reinterpret_cast(&_headData->_lookAtPosition), sizeof(_headData->_lookAtPosition)); // Instantaneous audio loudness (used to drive facial animation) //sourceBuffer += unpackFloatFromByte(sourceBuffer, _audioLoudness, MAX_AUDIO_LOUDNESS); - memcpy(&_headData->_audioLoudness, sourceBuffer, sizeof(float)); - sourceBuffer += sizeof(float); + packetStream >> _headData->_audioLoudness; // the rest is a chat message - int chatMessageSize = *sourceBuffer++; - _chatMessage = string((char*)sourceBuffer, chatMessageSize); - sourceBuffer += chatMessageSize * sizeof(char); + + quint8 chatMessageSize; + packetStream >> chatMessageSize; + _chatMessage = string(packet.data() + packetStream.device()->pos(), chatMessageSize); + packetStream.skipRawData(chatMessageSize); // voxel sending features... unsigned char bitItems = 0; - bitItems = (unsigned char)*sourceBuffer++; - + packetStream >> bitItems; + // key state, stored as a semi-nibble in the bitItems _keyState = (KeyState)getSemiNibbleAt(bitItems,KEY_STATE_START_BIT); @@ -239,34 +244,31 @@ int AvatarData::parseData(unsigned char* sourceBuffer, int numBytes) { // If it is connected, pack up the data if (_headData->_isFaceshiftConnected) { - memcpy(&_headData->_leftEyeBlink, sourceBuffer, sizeof(float)); - sourceBuffer += sizeof(float); - - memcpy(&_headData->_rightEyeBlink, sourceBuffer, sizeof(float)); - sourceBuffer += sizeof(float); - - memcpy(&_headData->_averageLoudness, sourceBuffer, sizeof(float)); - sourceBuffer += sizeof(float); - - memcpy(&_headData->_browAudioLift, sourceBuffer, sizeof(float)); - sourceBuffer += sizeof(float); + packetStream >> _headData->_leftEyeBlink; + packetStream >> _headData->_rightEyeBlink; + packetStream >> _headData->_averageLoudness; + packetStream >> _headData->_browAudioLift; - _headData->_blendshapeCoefficients.resize(*sourceBuffer++); - memcpy(_headData->_blendshapeCoefficients.data(), sourceBuffer, - _headData->_blendshapeCoefficients.size() * sizeof(float)); - sourceBuffer += _headData->_blendshapeCoefficients.size() * sizeof(float); + quint8 numBlendshapeCoefficients; + packetStream >> numBlendshapeCoefficients; + + _headData->_blendshapeCoefficients.resize(numBlendshapeCoefficients); + packetStream.readRawData(reinterpret_cast(_headData->_blendshapeCoefficients.data()), + numBlendshapeCoefficients * sizeof(float)); } // pupil dilation - sourceBuffer += unpackFloatFromByte(sourceBuffer, _headData->_pupilDilation, 1.0f); + quint8 pupilByte; + packetStream >> pupilByte; + unpackFloatFromByte(&pupilByte, _headData->_pupilDilation, 1.0f); // leap hand data - if (sourceBuffer - startPosition < numBytes) { + if (packetStream.device()->pos() < packet.size()) { // check passed, bytes match - sourceBuffer += _handData->decodeRemoteData(sourceBuffer); + packetStream.skipRawData(_handData->decodeRemoteData(packet.mid(packetStream.device()->pos()))); } - return sourceBuffer - startPosition; + return packetStream.device()->pos(); } void AvatarData::setClampedTargetScale(float targetScale) { diff --git a/libraries/avatars/src/AvatarData.h b/libraries/avatars/src/AvatarData.h index fc9bad7f02..bc16f2baaa 100755 --- a/libraries/avatars/src/AvatarData.h +++ b/libraries/avatars/src/AvatarData.h @@ -79,8 +79,8 @@ public: glm::vec3 getHandPosition() const; void setHandPosition(const glm::vec3& handPosition); - int getBroadcastData(unsigned char* destinationBuffer); - int parseData(unsigned char* sourceBuffer, int numBytes); + QByteArray toByteArray(); + int parseData(const QByteArray& packet); // Body Rotation float getBodyYaw() const { return _bodyYaw; } diff --git a/libraries/avatars/src/HandData.cpp b/libraries/avatars/src/HandData.cpp index 81d4469486..9342c2c6ed 100644 --- a/libraries/avatars/src/HandData.cpp +++ b/libraries/avatars/src/HandData.cpp @@ -157,10 +157,11 @@ int HandData::encodeRemoteData(unsigned char* destinationBuffer) { return destinationBuffer - startPosition; } -int HandData::decodeRemoteData(unsigned char* sourceBuffer) { - const unsigned char* startPosition = sourceBuffer; - - unsigned int numHands = *sourceBuffer++; +int HandData::decodeRemoteData(const QByteArray& dataByteArray) { + QDataStream packetStream(dataByteArray); + + quint8 numHands; + packetStream >> numHands; for (unsigned int handIndex = 0; handIndex < numHands; ++handIndex) { if (handIndex >= getNumPalms()) @@ -169,9 +170,18 @@ int HandData::decodeRemoteData(unsigned char* sourceBuffer) { glm::vec3 handPosition; glm::vec3 handNormal; - sourceBuffer += unpackFloatVec3FromSignedTwoByteFixed(sourceBuffer, handPosition, fingerVectorRadix); - sourceBuffer += unpackFloatVec3FromSignedTwoByteFixed(sourceBuffer, handNormal, fingerVectorRadix); - unsigned int numFingers = *sourceBuffer++; + qint16 twoByteHolder; + + packetStream >> twoByteHolder; + unpackFloatVec3FromSignedTwoByteFixed(reinterpret_cast(&twoByteHolder), + handPosition, fingerVectorRadix); + + packetStream >> twoByteHolder; + unpackFloatVec3FromSignedTwoByteFixed(reinterpret_cast(&twoByteHolder), + handNormal, fingerVectorRadix); + + quint8 numFingers; + packetStream >> numFingers; palm.setRawPosition(handPosition); palm.setRawNormal(handNormal); @@ -186,8 +196,14 @@ int HandData::decodeRemoteData(unsigned char* sourceBuffer) { glm::vec3 tipPosition; glm::vec3 rootPosition; - sourceBuffer += unpackFloatVec3FromSignedTwoByteFixed(sourceBuffer, tipPosition, fingerVectorRadix); - sourceBuffer += unpackFloatVec3FromSignedTwoByteFixed(sourceBuffer, rootPosition, fingerVectorRadix); + + packetStream >> twoByteHolder; + unpackFloatVec3FromSignedTwoByteFixed(reinterpret_cast(&twoByteHolder), tipPosition, + fingerVectorRadix); + + packetStream >> twoByteHolder; + unpackFloatVec3FromSignedTwoByteFixed(reinterpret_cast(&twoByteHolder), rootPosition, + fingerVectorRadix); finger.setRawTipPosition(tipPosition); finger.setRawRootPosition(rootPosition); @@ -207,11 +223,14 @@ int HandData::decodeRemoteData(unsigned char* sourceBuffer) { } // One byte for error checking safety. - unsigned char requiredLength = (unsigned char)(sourceBuffer - startPosition); - unsigned char checkLength = *sourceBuffer++; + unsigned char requiredLength = packetStream.device()->pos(); + + unsigned char checkLength; + packetStream >> checkLength; + assert(checkLength == requiredLength); - return sourceBuffer - startPosition; + return packetStream.device()->pos(); } void HandData::setFingerTrailLength(unsigned int length) { diff --git a/libraries/avatars/src/HandData.h b/libraries/avatars/src/HandData.h index 0f1e393db9..5c0a01540d 100755 --- a/libraries/avatars/src/HandData.h +++ b/libraries/avatars/src/HandData.h @@ -73,7 +73,7 @@ public: // Use these for sending and receiving hand data int encodeRemoteData(unsigned char* destinationBuffer); - int decodeRemoteData(unsigned char* sourceBuffer); + int decodeRemoteData(const QByteArray& dataByteArray); /// Checks for penetration between the described sphere and the hand. /// \param penetratorCenter the center of the penetration test sphere diff --git a/libraries/metavoxels/src/MetavoxelUtil.cpp b/libraries/metavoxels/src/MetavoxelUtil.cpp index 29b8c57168..1ea76d168f 100644 --- a/libraries/metavoxels/src/MetavoxelUtil.cpp +++ b/libraries/metavoxels/src/MetavoxelUtil.cpp @@ -16,7 +16,7 @@ QUuid readSessionID(const QByteArray& data, const HifiSockAddr& sender, int& headerPlusIDSize) { // get the header size - int headerSize = numBytesForPacketHeader(reinterpret_cast(data.constData())); + int headerSize = numBytesForPacketHeader(data); // read the session id const int UUID_BYTES = 16; diff --git a/libraries/octree-server/src/OctreeInboundPacketProcessor.cpp b/libraries/octree-server/src/OctreeInboundPacketProcessor.cpp index e537838649..fd5e9f1749 100644 --- a/libraries/octree-server/src/OctreeInboundPacketProcessor.cpp +++ b/libraries/octree-server/src/OctreeInboundPacketProcessor.cpp @@ -39,25 +39,26 @@ void OctreeInboundPacketProcessor::resetStats() { } -void OctreeInboundPacketProcessor::processPacket(const HifiSockAddr& senderSockAddr, - unsigned char* packetData, ssize_t packetLength) { +void OctreeInboundPacketProcessor::processPacket(const HifiSockAddr& senderSockAddr, const QByteArray& packet) { bool debugProcessPacket = _myServer->wantsVerboseDebug(); if (debugProcessPacket) { - printf("OctreeInboundPacketProcessor::processPacket() packetData=%p packetLength=%ld\n", packetData, packetLength); + printf("OctreeInboundPacketProcessor::processPacket() packetData=%p packetLength=%d\n", &packet, packet.size()); } - int numBytesPacketHeader = numBytesForPacketHeader(packetData); + int numBytesPacketHeader = numBytesForPacketHeader(packet); // Ask our tree subclass if it can handle the incoming packet... - PACKET_TYPE packetType = packetData[0]; + PacketType packetType = packetTypeForPacket(packet); if (_myServer->getOctree()->handlesEditPacketType(packetType)) { PerformanceWarning warn(debugProcessPacket, "processPacket KNOWN TYPE",debugProcessPacket); _receivedPacketCount++; SharedNodePointer senderNode = NodeList::getInstance()->nodeWithAddress(senderSockAddr); + + const unsigned char* packetData = reinterpret_cast(packet.data()); unsigned short int sequence = (*((unsigned short int*)(packetData + numBytesPacketHeader))); uint64_t sentAt = (*((uint64_t*)(packetData + numBytesPacketHeader + sizeof(sequence)))); @@ -69,26 +70,26 @@ void OctreeInboundPacketProcessor::processPacket(const HifiSockAddr& senderSockA if (_myServer->wantsDebugReceiving()) { qDebug() << "PROCESSING THREAD: got '" << packetType << "' packet - " << _receivedPacketCount - << " command from client receivedBytes=" << packetLength + << " command from client receivedBytes=" << packet.size() << " sequence=" << sequence << " transitTime=" << transitTime << " usecs"; } int atByte = numBytesPacketHeader + sizeof(sequence) + sizeof(sentAt); unsigned char* editData = (unsigned char*)&packetData[atByte]; - while (atByte < packetLength) { - int maxSize = packetLength - atByte; + while (atByte < packet.size()) { + int maxSize = packet.size() - atByte; if (debugProcessPacket) { printf("OctreeInboundPacketProcessor::processPacket() %c " - "packetData=%p packetLength=%ld voxelData=%p atByte=%d maxSize=%d\n", - packetType, packetData, packetLength, editData, atByte, maxSize); + "packetData=%p packetLength=%d voxelData=%p atByte=%d maxSize=%d\n", + packetType, packetData, packet.size(), editData, atByte, maxSize); } uint64_t startLock = usecTimestampNow(); _myServer->getOctree()->lockForWrite(); uint64_t startProcess = usecTimestampNow(); int editDataBytesRead = _myServer->getOctree()->processEditPacketData(packetType, - packetData, - packetLength, + reinterpret_cast(packet.data()), + packet.size(), editData, maxSize, senderNode.data()); _myServer->getOctree()->unlock(); uint64_t endProcess = usecTimestampNow(); @@ -106,8 +107,8 @@ void OctreeInboundPacketProcessor::processPacket(const HifiSockAddr& senderSockA if (debugProcessPacket) { printf("OctreeInboundPacketProcessor::processPacket() DONE LOOPING FOR %c " - "packetData=%p packetLength=%ld voxelData=%p atByte=%d\n", - packetType, packetData, packetLength, editData, atByte); + "packetData=%p packetLength=%d voxelData=%p atByte=%d\n", + packetType, packetData, packet.size(), editData, atByte); } // Make sure our Node and NodeList knows we've heard from this node. @@ -125,7 +126,7 @@ void OctreeInboundPacketProcessor::processPacket(const HifiSockAddr& senderSockA } trackInboundPackets(nodeUUID, sequence, transitTime, editsInPacket, processTime, lockWaitTime); } else { - qDebug("unknown packet ignored... packetData[0]=%c", packetData[0]); + qDebug("unknown packet ignored... packetType=%d", packetType); } } diff --git a/libraries/octree-server/src/OctreeInboundPacketProcessor.h b/libraries/octree-server/src/OctreeInboundPacketProcessor.h index 51214b2617..a4d40e8ae1 100644 --- a/libraries/octree-server/src/OctreeInboundPacketProcessor.h +++ b/libraries/octree-server/src/OctreeInboundPacketProcessor.h @@ -63,7 +63,7 @@ public: NodeToSenderStatsMap& getSingleSenderStats() { return _singleSenderStats; } protected: - virtual void processPacket(const HifiSockAddr& senderSockAddr, unsigned char* packetData, ssize_t packetLength); + virtual void processPacket(const HifiSockAddr& senderSockAddr, const QByteArray& packet); private: void trackInboundPackets(const QUuid& nodeUUID, int sequence, uint64_t transitTime, diff --git a/libraries/octree-server/src/OctreeQueryNode.cpp b/libraries/octree-server/src/OctreeQueryNode.cpp index f220180980..e454658f07 100644 --- a/libraries/octree-server/src/OctreeQueryNode.cpp +++ b/libraries/octree-server/src/OctreeQueryNode.cpp @@ -110,7 +110,7 @@ void OctreeQueryNode::resetOctreePacket(bool lastWasSurpressed) { } _octreePacketAvailableBytes = MAX_PACKET_SIZE; - int numBytesPacketHeader = populateTypeAndVersion(_octreePacket, getMyPacketType()); + int numBytesPacketHeader = populatePacketHeader(reinterpret_cast(_octreePacket), getMyPacketType()); _octreePacketAt = _octreePacket + numBytesPacketHeader; _octreePacketAvailableBytes -= numBytesPacketHeader; diff --git a/libraries/octree-server/src/OctreeQueryNode.h b/libraries/octree-server/src/OctreeQueryNode.h index 6fc3c1a07b..c151bb0697 100644 --- a/libraries/octree-server/src/OctreeQueryNode.h +++ b/libraries/octree-server/src/OctreeQueryNode.h @@ -27,7 +27,7 @@ public: OctreeQueryNode(); virtual ~OctreeQueryNode(); - virtual PACKET_TYPE getMyPacketType() const = 0; + virtual PacketType getMyPacketType() const = 0; void resetOctreePacket(bool lastWasSurpressed = false); // resets octree packet to after "V" header diff --git a/libraries/octree-server/src/OctreeSendThread.cpp b/libraries/octree-server/src/OctreeSendThread.cpp index a12a633e58..7c63d4b0cd 100644 --- a/libraries/octree-server/src/OctreeSendThread.cpp +++ b/libraries/octree-server/src/OctreeSendThread.cpp @@ -101,7 +101,7 @@ int OctreeSendThread::handlePacketSend(Node* node, OctreeQueryNode* nodeData, in } const unsigned char* messageData = nodeData->getPacket(); - int numBytesPacketHeader = numBytesForPacketHeader(messageData); + int numBytesPacketHeader = numBytesForPacketHeader(reinterpret_cast(messageData)); const unsigned char* dataAt = messageData + numBytesPacketHeader; dataAt += sizeof(OCTREE_PACKET_FLAGS); OCTREE_PACKET_SEQUENCE sequence = (*(OCTREE_PACKET_SEQUENCE*)dataAt); diff --git a/libraries/octree-server/src/OctreeServer.cpp b/libraries/octree-server/src/OctreeServer.cpp index 438f71dd16..9a3ce9aebc 100644 --- a/libraries/octree-server/src/OctreeServer.cpp +++ b/libraries/octree-server/src/OctreeServer.cpp @@ -28,8 +28,8 @@ void OctreeServer::attachQueryNodeToNode(Node* newNode) { } } -OctreeServer::OctreeServer(const unsigned char* dataBuffer, int numBytes) : - ThreadedAssignment(dataBuffer, numBytes), +OctreeServer::OctreeServer(const QByteArray& packet) : + ThreadedAssignment(packet), _argc(0), _argv(NULL), _parsedArgV(NULL), @@ -432,7 +432,7 @@ void OctreeServer::setArguments(int argc, char** argv) { void OctreeServer::parsePayload() { - if (getNumPayloadBytes() > 0) { + if (getPayload().size() > 0) { QString config((const char*) _payload); // Now, parse the config @@ -461,26 +461,23 @@ void OctreeServer::parsePayload() { void OctreeServer::processDatagram(const QByteArray& dataByteArray, const HifiSockAddr& senderSockAddr) { NodeList* nodeList = NodeList::getInstance(); - PACKET_TYPE packetType = dataByteArray[0]; + PacketType packetType = packetTypeForPacket(dataByteArray); if (packetType == getMyQueryMessageType()) { bool debug = false; if (debug) { - qDebug() << "Got PACKET_TYPE_VOXEL_QUERY at" << usecTimestampNow(); + qDebug() << "Got PacketType_VOXEL_QUERY at" << usecTimestampNow(); } - - int numBytesPacketHeader = numBytesForPacketHeader((unsigned char*) dataByteArray.data()); - - // If we got a PACKET_TYPE_VOXEL_QUERY, then we're talking to an NODE_TYPE_AVATAR, and we + + // If we got a PacketType_VOXEL_QUERY, then we're talking to an NODE_TYPE_AVATAR, and we // need to make sure we have it in our nodeList. - QUuid nodeUUID = QUuid::fromRfc4122(dataByteArray.mid(numBytesPacketHeader, - NUM_BYTES_RFC4122_UUID)); + QUuid nodeUUID; + deconstructPacketHeader(dataByteArray, nodeUUID); SharedNodePointer node = nodeList->nodeWithUUID(nodeUUID); if (node) { - nodeList->updateNodeWithData(node.data(), senderSockAddr, (unsigned char *) dataByteArray.data(), - dataByteArray.size()); + nodeList->updateNodeWithData(node.data(), senderSockAddr, dataByteArray); if (!node->getActiveSocket()) { // we don't have an active socket for this node, but they're talking to us // this means they've heard from us and can reply, let's assume public is active @@ -491,16 +488,13 @@ void OctreeServer::processDatagram(const QByteArray& dataByteArray, const HifiSo nodeData->initializeOctreeSendThread(this, nodeUUID); } } - } else if (packetType == PACKET_TYPE_JURISDICTION_REQUEST) { - _jurisdictionSender->queueReceivedPacket(senderSockAddr, (unsigned char*) dataByteArray.data(), - dataByteArray.size()); + } else if (packetType == PacketTypeJurisdictionRequest) { + _jurisdictionSender->queueReceivedPacket(senderSockAddr, dataByteArray); } else if (_octreeInboundPacketProcessor && getOctree()->handlesEditPacketType(packetType)) { - _octreeInboundPacketProcessor->queueReceivedPacket(senderSockAddr, (unsigned char*) dataByteArray.data(), - dataByteArray.size()); + _octreeInboundPacketProcessor->queueReceivedPacket(senderSockAddr, dataByteArray); } else { // let processNodeData handle it. - NodeList::getInstance()->processNodeData(senderSockAddr, (unsigned char*) dataByteArray.data(), - dataByteArray.size()); + NodeList::getInstance()->processNodeData(senderSockAddr, dataByteArray); } } @@ -512,7 +506,7 @@ void OctreeServer::run() { Logging::setTargetName(getMyLoggingServerTargetName()); // Now would be a good time to parse our arguments, if we got them as assignment - if (getNumPayloadBytes() > 0) { + if (getPayload().size() > 0) { parsePayload(); } diff --git a/libraries/octree-server/src/OctreeServer.h b/libraries/octree-server/src/OctreeServer.h index 86ad134df0..b17beb4a7e 100644 --- a/libraries/octree-server/src/OctreeServer.h +++ b/libraries/octree-server/src/OctreeServer.h @@ -28,7 +28,7 @@ class OctreeServer : public ThreadedAssignment, public HTTPRequestHandler { Q_OBJECT public: - OctreeServer(const unsigned char* dataBuffer, int numBytes); + OctreeServer(const QByteArray& packet); ~OctreeServer(); /// allows setting of run arguments @@ -51,7 +51,7 @@ public: virtual OctreeQueryNode* createOctreeQueryNode() = 0; virtual Octree* createTree() = 0; virtual unsigned char getMyNodeType() const = 0; - virtual PACKET_TYPE getMyQueryMessageType() const = 0; + virtual PacketType getMyQueryMessageType() const = 0; virtual const char* getMyServerName() const = 0; virtual const char* getMyLoggingServerTargetName() const = 0; virtual const char* getMyDefaultPersistFilename() const = 0; diff --git a/libraries/octree/src/JurisdictionListener.cpp b/libraries/octree/src/JurisdictionListener.cpp index e761a15e76..e28fb92cdb 100644 --- a/libraries/octree/src/JurisdictionListener.cpp +++ b/libraries/octree/src/JurisdictionListener.cpp @@ -39,7 +39,7 @@ bool JurisdictionListener::queueJurisdictionRequest() { static unsigned char buffer[MAX_PACKET_SIZE]; unsigned char* bufferOut = &buffer[0]; - ssize_t sizeOut = populateTypeAndVersion(bufferOut, PACKET_TYPE_JURISDICTION_REQUEST); + ssize_t sizeOut = populatePacketHeader(reinterpret_cast(bufferOut), PacketTypeJurisdictionRequest); int nodeCount = 0; NodeList* nodeList = NodeList::getInstance(); @@ -48,7 +48,7 @@ bool JurisdictionListener::queueJurisdictionRequest() { if (nodeList->getNodeActiveSocketOrPing(node.data()) && node->getType() == getNodeType()) { const HifiSockAddr* nodeAddress = node->getActiveSocket(); - _packetSender.queuePacketForSending(*nodeAddress, bufferOut, sizeOut); + _packetSender.queuePacketForSending(*nodeAddress, QByteArray(reinterpret_cast(bufferOut), sizeOut)); nodeCount++; } } @@ -63,14 +63,14 @@ bool JurisdictionListener::queueJurisdictionRequest() { return isStillRunning(); } -void JurisdictionListener::processPacket(const HifiSockAddr& senderAddress, unsigned char* packetData, ssize_t packetLength) { +void JurisdictionListener::processPacket(const HifiSockAddr& senderAddress, const QByteArray& packet) { //qDebug() << "JurisdictionListener::processPacket()"; - if (packetData[0] == PACKET_TYPE_JURISDICTION) { + if (packetTypeForPacket(packet) == PacketTypeJurisdictionRequest) { SharedNodePointer node = NodeList::getInstance()->nodeWithAddress(senderAddress); if (node) { QUuid nodeUUID = node->getUUID(); JurisdictionMap map; - map.unpackFromMessage(packetData, packetLength); + map.unpackFromMessage(reinterpret_cast(packet.data()), packet.size()); _jurisdictions[nodeUUID] = map; } } diff --git a/libraries/octree/src/JurisdictionListener.h b/libraries/octree/src/JurisdictionListener.h index fea76f57eb..d4cd396a48 100644 --- a/libraries/octree/src/JurisdictionListener.h +++ b/libraries/octree/src/JurisdictionListener.h @@ -18,8 +18,8 @@ #include "JurisdictionMap.h" -/// Sends out PACKET_TYPE_JURISDICTION_REQUEST packets to all voxel servers and then listens for and processes -/// the PACKET_TYPE_JURISDICTION packets it receives in order to maintain an accurate state of all jurisidictions +/// Sends out PacketType_JURISDICTION_REQUEST packets to all voxel servers and then listens for and processes +/// the PacketType_JURISDICTION packets it receives in order to maintain an accurate state of all jurisidictions /// within the domain. As with other ReceivedPacketProcessor classes the user is responsible for reading inbound packets /// and adding them to the processing queue by calling queueReceivedPacket() class JurisdictionListener : public ReceivedPacketProcessor { @@ -43,13 +43,13 @@ public slots: void nodeKilled(SharedNodePointer node); protected: - /// Callback for processing of received packets. Will process any queued PACKET_TYPE_JURISDICTION and update the + /// Callback for processing of received packets. Will process any queued PacketType_JURISDICTION and update the /// jurisdiction map member variable /// \param sockaddr& senderAddress the address of the sender /// \param packetData pointer to received data /// \param ssize_t packetLength size of received data /// \thread "this" individual processing thread - virtual void processPacket(const HifiSockAddr& senderAddress, unsigned char* packetData, ssize_t packetLength); + virtual void processPacket(const HifiSockAddr& senderAddress, const QByteArray& packet); private: NodeToJurisdictionMap _jurisdictions; diff --git a/libraries/octree/src/JurisdictionMap.cpp b/libraries/octree/src/JurisdictionMap.cpp index bf64e19959..df980917e8 100644 --- a/libraries/octree/src/JurisdictionMap.cpp +++ b/libraries/octree/src/JurisdictionMap.cpp @@ -265,7 +265,7 @@ bool JurisdictionMap::writeToFile(const char* filename) { int JurisdictionMap::packEmptyJurisdictionIntoMessage(NODE_TYPE type, unsigned char* destinationBuffer, int availableBytes) { unsigned char* bufferStart = destinationBuffer; - int headerLength = populateTypeAndVersion(destinationBuffer, PACKET_TYPE_JURISDICTION); + int headerLength = populatePacketHeader(reinterpret_cast(destinationBuffer), PacketTypeJurisdiction); destinationBuffer += headerLength; // Pack the Node Type in first byte @@ -283,7 +283,7 @@ int JurisdictionMap::packEmptyJurisdictionIntoMessage(NODE_TYPE type, unsigned c int JurisdictionMap::packIntoMessage(unsigned char* destinationBuffer, int availableBytes) { unsigned char* bufferStart = destinationBuffer; - int headerLength = populateTypeAndVersion(destinationBuffer, PACKET_TYPE_JURISDICTION); + int headerLength = populatePacketHeader(reinterpret_cast(destinationBuffer), PacketTypeJurisdiction); destinationBuffer += headerLength; // Pack the Node Type in first byte @@ -324,12 +324,12 @@ int JurisdictionMap::packIntoMessage(unsigned char* destinationBuffer, int avail return destinationBuffer - bufferStart; // includes header! } -int JurisdictionMap::unpackFromMessage(unsigned char* sourceBuffer, int availableBytes) { +int JurisdictionMap::unpackFromMessage(const unsigned char* sourceBuffer, int availableBytes) { clear(); - unsigned char* startPosition = sourceBuffer; + const unsigned char* startPosition = sourceBuffer; // increment to push past the packet header - int numBytesPacketHeader = numBytesForPacketHeader(sourceBuffer); + int numBytesPacketHeader = numBytesForPacketHeader(reinterpret_cast(sourceBuffer)); sourceBuffer += numBytesPacketHeader; int remainingBytes = availableBytes - numBytesPacketHeader; diff --git a/libraries/octree/src/JurisdictionMap.h b/libraries/octree/src/JurisdictionMap.h index 44c1cfa3cf..5380a0167a 100644 --- a/libraries/octree/src/JurisdictionMap.h +++ b/libraries/octree/src/JurisdictionMap.h @@ -16,7 +16,7 @@ #include #include -#include +#include class JurisdictionMap { public: @@ -56,7 +56,7 @@ public: void copyContents(unsigned char* rootCodeIn, const std::vector& endNodesIn); - int unpackFromMessage(unsigned char* sourceBuffer, int availableBytes); + int unpackFromMessage(const unsigned char* sourceBuffer, int availableBytes); int packIntoMessage(unsigned char* destinationBuffer, int availableBytes); /// Available to pack an empty or unknown jurisdiction into a network packet, used when no JurisdictionMap is available diff --git a/libraries/octree/src/JurisdictionSender.cpp b/libraries/octree/src/JurisdictionSender.cpp index e1bbf78506..f3ee5def2e 100644 --- a/libraries/octree/src/JurisdictionSender.cpp +++ b/libraries/octree/src/JurisdictionSender.cpp @@ -28,11 +28,11 @@ JurisdictionSender::~JurisdictionSender() { } -void JurisdictionSender::processPacket(const HifiSockAddr& senderAddress, unsigned char* packetData, ssize_t packetLength) { - if (packetData[0] == PACKET_TYPE_JURISDICTION_REQUEST) { - SharedNodePointer node = NodeList::getInstance()->nodeWithAddress(senderAddress); - if (node) { - QUuid nodeUUID = node->getUUID(); +void JurisdictionSender::processPacket(const HifiSockAddr& senderAddress, const QByteArray& packet) { + if (packetTypeForPacket(packet) == PacketTypeJurisdictionRequest) { + QUuid nodeUUID; + deconstructPacketHeader(packet, nodeUUID); + if (!nodeUUID.isNull()) { lockRequestingNodes(); _nodesRequestingJurisdictions.push(nodeUUID); unlockRequestingNodes(); @@ -66,7 +66,7 @@ bool JurisdictionSender::process() { if (node->getActiveSocket() != NULL) { const HifiSockAddr* nodeAddress = node->getActiveSocket(); - _packetSender.queuePacketForSending(*nodeAddress, bufferOut, sizeOut); + _packetSender.queuePacketForSending(*nodeAddress, QByteArray(reinterpret_cast(bufferOut), sizeOut)); nodeCount++; } } diff --git a/libraries/octree/src/JurisdictionSender.h b/libraries/octree/src/JurisdictionSender.h index e70070b21d..7c8f288728 100644 --- a/libraries/octree/src/JurisdictionSender.h +++ b/libraries/octree/src/JurisdictionSender.h @@ -18,7 +18,7 @@ #include #include "JurisdictionMap.h" -/// Will process PACKET_TYPE_JURISDICTION_REQUEST packets and send out PACKET_TYPE_JURISDICTION packets +/// Will process PacketType_JURISDICTION_REQUEST packets and send out PacketType_JURISDICTION packets /// to requesting parties. As with other ReceivedPacketProcessor classes the user is responsible for reading inbound packets /// and adding them to the processing queue by calling queueReceivedPacket() class JurisdictionSender : public ReceivedPacketProcessor { @@ -37,7 +37,7 @@ public: void setNodeType(NODE_TYPE type) { _nodeType = type; } protected: - virtual void processPacket(const HifiSockAddr& senderAddress, unsigned char* packetData, ssize_t packetLength); + virtual void processPacket(const HifiSockAddr& senderAddress, const QByteArray& packet); /// Locks all the resources of the thread. void lockRequestingNodes() { _requestingNodeMutex.lock(); } diff --git a/libraries/octree/src/Octree.cpp b/libraries/octree/src/Octree.cpp index 5d25f0c164..d204d6487c 100644 --- a/libraries/octree/src/Octree.cpp +++ b/libraries/octree/src/Octree.cpp @@ -443,7 +443,7 @@ void Octree::eraseAllOctreeElements() { void Octree::processRemoveOctreeElementsBitstream(const unsigned char* bitstream, int bufferSizeBytes) { //unsigned short int itemNumber = (*((unsigned short int*)&bitstream[sizeof(PACKET_HEADER)])); - int numBytesPacketHeader = numBytesForPacketHeader(bitstream); + int numBytesPacketHeader = numBytesForPacketHeader(reinterpret_cast(bitstream)); unsigned short int sequence = (*((unsigned short int*)(bitstream + numBytesPacketHeader))); uint64_t sentAt = (*((uint64_t*)(bitstream + numBytesPacketHeader + sizeof(sequence)))); @@ -1322,13 +1322,16 @@ bool Octree::readFromSVOFile(const char* fileName) { // before reading the file, check to see if this version of the Octree supports file versions if (getWantSVOfileVersions()) { // if so, read the first byte of the file and see if it matches the expected version code - PACKET_TYPE expectedType = expectedDataPacketType(); - PACKET_TYPE gotType = *dataAt; + PacketType expectedType = expectedDataPacketType(); + + PacketType gotType; + memcpy(&gotType, dataAt, sizeof(gotType)); + if (gotType == expectedType) { dataAt += sizeof(expectedType); dataLength -= sizeof(expectedType); - PACKET_VERSION expectedVersion = versionForPacketType(expectedType); - PACKET_VERSION gotVersion = *dataAt; + PacketVersion expectedVersion = versionForPacketType(expectedType); + PacketVersion gotVersion = *dataAt; if (gotVersion == expectedVersion) { dataAt += sizeof(expectedVersion); dataLength -= sizeof(expectedVersion); @@ -1365,9 +1368,9 @@ void Octree::writeToSVOFile(const char* fileName, OctreeElement* node) { // before reading the file, check to see if this version of the Octree supports file versions if (getWantSVOfileVersions()) { // if so, read the first byte of the file and see if it matches the expected version code - PACKET_TYPE expectedType = expectedDataPacketType(); - PACKET_VERSION expectedVersion = versionForPacketType(expectedType); - file.write(&expectedType, sizeof(expectedType)); + PacketType expectedType = expectedDataPacketType(); + PacketVersion expectedVersion = versionForPacketType(expectedType); + file.write(reinterpret_cast(&expectedType), sizeof(expectedType)); file.write(&expectedVersion, sizeof(expectedVersion)); } diff --git a/libraries/octree/src/Octree.h b/libraries/octree/src/Octree.h index 959c9272cf..8ca7dec0e6 100644 --- a/libraries/octree/src/Octree.h +++ b/libraries/octree/src/Octree.h @@ -187,10 +187,10 @@ public: // These methods will allow the OctreeServer to send your tree inbound edit packets of your // own definition. Implement these to allow your octree based server to support editing virtual bool getWantSVOfileVersions() const { return false; } - virtual PACKET_TYPE expectedDataPacketType() const { return PACKET_TYPE_UNKNOWN; } - virtual bool handlesEditPacketType(PACKET_TYPE packetType) const { return false; } - virtual int processEditPacketData(PACKET_TYPE packetType, unsigned char* packetData, int packetLength, - unsigned char* editData, int maxLength, Node* senderNode) { return 0; } + virtual PacketType expectedDataPacketType() const { return PacketTypeUnknown; } + virtual bool handlesEditPacketType(PacketType packetType) const { return false; } + virtual int processEditPacketData(PacketType packetType, const unsigned char* packetData, int packetLength, + const unsigned char* editData, int maxLength, Node* senderNode) { return 0; } virtual void update() { }; // nothing to do by default diff --git a/libraries/octree/src/OctreeEditPacketSender.cpp b/libraries/octree/src/OctreeEditPacketSender.cpp index d4c1051747..b8f38e3b0b 100644 --- a/libraries/octree/src/OctreeEditPacketSender.cpp +++ b/libraries/octree/src/OctreeEditPacketSender.cpp @@ -17,7 +17,7 @@ #include "OctreeEditPacketSender.h" -EditPacketBuffer::EditPacketBuffer(PACKET_TYPE type, unsigned char* buffer, ssize_t length, QUuid nodeUUID) { +EditPacketBuffer::EditPacketBuffer(PacketType type, unsigned char* buffer, ssize_t length, QUuid nodeUUID) { _nodeUUID = nodeUUID; _currentType = type; _currentSize = length; @@ -93,12 +93,12 @@ void OctreeEditPacketSender::queuePacketToNode(const QUuid& nodeUUID, unsigned c ((node->getUUID() == nodeUUID) || (nodeUUID.isNull()))) { if (nodeList->getNodeActiveSocketOrPing(node.data())) { const HifiSockAddr* nodeAddress = node->getActiveSocket(); - queuePacketForSending(*nodeAddress, buffer, length); + queuePacketForSending(*nodeAddress, QByteArray(reinterpret_cast(buffer), length)); // debugging output... bool wantDebugging = false; if (wantDebugging) { - int numBytesPacketHeader = numBytesForPacketHeader(buffer); + int numBytesPacketHeader = numBytesForPacketHeader(reinterpret_cast(buffer)); unsigned short int sequence = (*((unsigned short int*)(buffer + numBytesPacketHeader))); uint64_t createdAt = (*((uint64_t*)(buffer + numBytesPacketHeader + sizeof(sequence)))); uint64_t queuedAt = usecTimestampNow(); @@ -141,7 +141,7 @@ void OctreeEditPacketSender::processPreServerExistsPackets() { } } -void OctreeEditPacketSender::queuePendingPacketToNodes(PACKET_TYPE type, unsigned char* buffer, ssize_t length) { +void OctreeEditPacketSender::queuePendingPacketToNodes(PacketType type, unsigned char* buffer, ssize_t length) { // If we're asked to save messages while waiting for voxel servers to arrive, then do so... if (_maxPendingMessages > 0) { EditPacketBuffer* packet = new EditPacketBuffer(type, buffer, length); @@ -163,7 +163,7 @@ void OctreeEditPacketSender::queuePacketToNodes(unsigned char* buffer, ssize_t l assert(serversExist()); // we must have jurisdictions to be here!! - int headerBytes = numBytesForPacketHeader(buffer) + sizeof(short) + sizeof(uint64_t); + int headerBytes = numBytesForPacketHeader(reinterpret_cast(buffer)) + sizeof(short) + sizeof(uint64_t); unsigned char* octCode = buffer + headerBytes; // skip the packet header to get to the octcode // We want to filter out edit messages for servers based on the server's Jurisdiction @@ -189,7 +189,7 @@ void OctreeEditPacketSender::queuePacketToNodes(unsigned char* buffer, ssize_t l // NOTE: codeColorBuffer - is JUST the octcode/color and does not contain the packet header! -void OctreeEditPacketSender::queueOctreeEditMessage(PACKET_TYPE type, unsigned char* codeColorBuffer, ssize_t length) { +void OctreeEditPacketSender::queueOctreeEditMessage(PacketType type, unsigned char* codeColorBuffer, ssize_t length) { if (!_shouldSend) { return; // bail early @@ -289,18 +289,18 @@ void OctreeEditPacketSender::releaseQueuedMessages() { } void OctreeEditPacketSender::releaseQueuedPacket(EditPacketBuffer& packetBuffer) { - if (packetBuffer._currentSize > 0 && packetBuffer._currentType != PACKET_TYPE_UNKNOWN) { + if (packetBuffer._currentSize > 0 && packetBuffer._currentType != PacketTypeUnknown) { //qDebug() << "OctreeEditPacketSender::releaseQueuedPacket() line:" << __LINE__; queuePacketToNode(packetBuffer._nodeUUID, &packetBuffer._currentBuffer[0], packetBuffer._currentSize); } packetBuffer._currentSize = 0; - packetBuffer._currentType = PACKET_TYPE_UNKNOWN; + packetBuffer._currentType = PacketTypeUnknown; } -void OctreeEditPacketSender::initializePacket(EditPacketBuffer& packetBuffer, PACKET_TYPE type) { - packetBuffer._currentSize = populateTypeAndVersion(&packetBuffer._currentBuffer[0], type); +void OctreeEditPacketSender::initializePacket(EditPacketBuffer& packetBuffer, PacketType type) { + packetBuffer._currentSize = populatePacketHeader(reinterpret_cast(&packetBuffer._currentBuffer[0]), type); - // pack in sequence number + // pack in sequence numbers unsigned short int* sequenceAt = (unsigned short int*)&packetBuffer._currentBuffer[packetBuffer._currentSize]; *sequenceAt = _sequenceNumber; packetBuffer._currentSize += sizeof(unsigned short int); // nudge past sequence diff --git a/libraries/octree/src/OctreeEditPacketSender.h b/libraries/octree/src/OctreeEditPacketSender.h index f214796f9d..3f20ed45a3 100644 --- a/libraries/octree/src/OctreeEditPacketSender.h +++ b/libraries/octree/src/OctreeEditPacketSender.h @@ -18,10 +18,10 @@ /// Used for construction of edit packets class EditPacketBuffer { public: - EditPacketBuffer() : _nodeUUID(), _currentType(PACKET_TYPE_UNKNOWN), _currentSize(0) { } - EditPacketBuffer(PACKET_TYPE type, unsigned char* codeColorBuffer, ssize_t length, const QUuid nodeUUID = QUuid()); + EditPacketBuffer() : _nodeUUID(), _currentType(PacketTypeUnknown), _currentSize(0) { } + EditPacketBuffer(PacketType type, unsigned char* codeColorBuffer, ssize_t length, const QUuid nodeUUID = QUuid()); QUuid _nodeUUID; - PACKET_TYPE _currentType; + PacketType _currentType; unsigned char _currentBuffer[MAX_PACKET_SIZE]; ssize_t _currentSize; }; @@ -36,7 +36,7 @@ public: /// Queues a single edit message. Will potentially send a pending multi-command packet. Determines which server /// node or nodes the packet should be sent to. Can be called even before servers are known, in which case up to /// MaxPendingMessages will be buffered and processed when servers are known. - void queueOctreeEditMessage(PACKET_TYPE type, unsigned char* buffer, ssize_t length); + void queueOctreeEditMessage(PacketType type, unsigned char* buffer, ssize_t length); /// Releases all queued messages even if those messages haven't filled an MTU packet. This will move the packed message /// packets onto the send queue. If running in threaded mode, the caller does not need to do any further processing to @@ -92,9 +92,9 @@ public: protected: bool _shouldSend; void queuePacketToNode(const QUuid& nodeID, unsigned char* buffer, ssize_t length); - void queuePendingPacketToNodes(PACKET_TYPE type, unsigned char* buffer, ssize_t length); + void queuePendingPacketToNodes(PacketType type, unsigned char* buffer, ssize_t length); void queuePacketToNodes(unsigned char* buffer, ssize_t length); - void initializePacket(EditPacketBuffer& packetBuffer, PACKET_TYPE type); + void initializePacket(EditPacketBuffer& packetBuffer, PacketType type); void releaseQueuedPacket(EditPacketBuffer& packetBuffer); // releases specific queued packet void processPreServerExistsPackets(); diff --git a/libraries/octree/src/OctreePacketData.h b/libraries/octree/src/OctreePacketData.h index 87b55ace96..1a2b160c81 100644 --- a/libraries/octree/src/OctreePacketData.h +++ b/libraries/octree/src/OctreePacketData.h @@ -28,7 +28,9 @@ typedef uint16_t OCTREE_PACKET_SEQUENCE; typedef uint64_t OCTREE_PACKET_SENT_TIME; typedef uint16_t OCTREE_PACKET_INTERNAL_SECTION_SIZE; const int MAX_OCTREE_PACKET_SIZE = MAX_PACKET_SIZE; -const int OCTREE_PACKET_HEADER_SIZE = (sizeof(PACKET_TYPE) + sizeof(PACKET_VERSION) + sizeof(OCTREE_PACKET_FLAGS) + +// this is overly conservative - sizeof(PacketType) is 8 bytes but a packed PacketType could be as small as one byte +const int OCTREE_PACKET_HEADER_SIZE = (sizeof(PacketType) + sizeof(PacketVersion) + sizeof(OCTREE_PACKET_FLAGS) + sizeof(OCTREE_PACKET_SEQUENCE) + sizeof(OCTREE_PACKET_SENT_TIME)); const int MAX_OCTREE_PACKET_DATA_SIZE = MAX_PACKET_SIZE - OCTREE_PACKET_HEADER_SIZE; @@ -60,7 +62,7 @@ private: int _bytesOfColor; }; -/// Handles packing of the data portion of PACKET_TYPE_OCTREE_DATA messages. +/// Handles packing of the data portion of PacketType_OCTREE_DATA messages. class OctreePacketData { public: OctreePacketData(bool enableCompression = false, int maxFinalizedSize = MAX_OCTREE_PACKET_DATA_SIZE); diff --git a/libraries/octree/src/OctreeQuery.cpp b/libraries/octree/src/OctreeQuery.cpp index ec474beb3d..51b73a9ed2 100644 --- a/libraries/octree/src/OctreeQuery.cpp +++ b/libraries/octree/src/OctreeQuery.cpp @@ -95,13 +95,13 @@ int OctreeQuery::getBroadcastData(unsigned char* destinationBuffer) { } // called on the other nodes - assigns it to my views of the others -int OctreeQuery::parseData(unsigned char* sourceBuffer, int numBytes) { +int OctreeQuery::parseData(const QByteArray& packet) { // increment to push past the packet header - int numBytesPacketHeader = numBytesForPacketHeader(sourceBuffer); - sourceBuffer += numBytesPacketHeader; + int numBytesPacketHeader = numBytesForPacketHeader(packet); - unsigned char* startPosition = sourceBuffer; + const unsigned char* startPosition = reinterpret_cast(packet.data()); + const unsigned char* sourceBuffer = startPosition + numBytesPacketHeader; // push past the node session UUID sourceBuffer += NUM_BYTES_RFC4122_UUID; diff --git a/libraries/octree/src/OctreeQuery.h b/libraries/octree/src/OctreeQuery.h index c306c5a851..98e27e48bd 100644 --- a/libraries/octree/src/OctreeQuery.h +++ b/libraries/octree/src/OctreeQuery.h @@ -55,7 +55,7 @@ public: virtual ~OctreeQuery(); int getBroadcastData(unsigned char* destinationBuffer); - int parseData(unsigned char* sourceBuffer, int numBytes); + int parseData(const QByteArray& packet); QUuid& getUUID() { return _uuid; } void setUUID(const QUuid& uuid) { _uuid = uuid; } diff --git a/libraries/octree/src/OctreeRenderer.cpp b/libraries/octree/src/OctreeRenderer.cpp index 7bbeb065d6..e53bd1a606 100644 --- a/libraries/octree/src/OctreeRenderer.cpp +++ b/libraries/octree/src/OctreeRenderer.cpp @@ -36,14 +36,14 @@ void OctreeRenderer::processDatagram(const QByteArray& dataByteArray, const Hifi unsigned char command = *packetData; - int numBytesPacketHeader = numBytesForPacketHeader(packetData); + int numBytesPacketHeader = numBytesForPacketHeader(dataByteArray); - PACKET_TYPE expectedType = getExpectedPacketType(); + PacketType expectedType = getExpectedPacketType(); if(command == expectedType) { - PerformanceWarning warn(showTimingDetails, "OctreeRenderer::processDatagram expected PACKET_TYPE",showTimingDetails); + PerformanceWarning warn(showTimingDetails, "OctreeRenderer::processDatagram expected PacketType",showTimingDetails); - const unsigned char* dataAt = packetData + numBytesPacketHeader; + const unsigned char* dataAt = reinterpret_cast(dataByteArray.data()) + numBytesPacketHeader; OCTREE_PACKET_FLAGS flags = (*(OCTREE_PACKET_FLAGS*)(dataAt)); dataAt += sizeof(OCTREE_PACKET_FLAGS); diff --git a/libraries/octree/src/OctreeRenderer.h b/libraries/octree/src/OctreeRenderer.h index f321ed2e3e..c1d3e85aef 100644 --- a/libraries/octree/src/OctreeRenderer.h +++ b/libraries/octree/src/OctreeRenderer.h @@ -13,9 +13,9 @@ #include #include -#include #include #include + #include "Octree.h" #include "OctreePacketData.h" #include "ViewFrustum.h" @@ -38,8 +38,8 @@ public: virtual Octree* createTree() = 0; virtual NODE_TYPE getMyNodeType() const = 0; - virtual PACKET_TYPE getMyQueryMessageType() const = 0; - virtual PACKET_TYPE getExpectedPacketType() const = 0; + virtual PacketType getMyQueryMessageType() const = 0; + virtual PacketType getExpectedPacketType() const = 0; virtual void renderElement(OctreeElement* element, RenderArgs* args) = 0; /// process incoming data diff --git a/libraries/octree/src/OctreeSceneStats.cpp b/libraries/octree/src/OctreeSceneStats.cpp index 35fe8a5d16..6a57fbf303 100644 --- a/libraries/octree/src/OctreeSceneStats.cpp +++ b/libraries/octree/src/OctreeSceneStats.cpp @@ -379,7 +379,7 @@ void OctreeSceneStats::childBitsRemoved(bool includesExistsBits, bool includesCo int OctreeSceneStats::packIntoMessage(unsigned char* destinationBuffer, int availableBytes) { unsigned char* bufferStart = destinationBuffer; - int headerLength = populateTypeAndVersion(destinationBuffer, PACKET_TYPE_OCTREE_STATS); + int headerLength = populatePacketHeader(reinterpret_cast(destinationBuffer), PacketTypeOctreeStats); destinationBuffer += headerLength; memcpy(destinationBuffer, &_start, sizeof(_start)); @@ -476,11 +476,11 @@ int OctreeSceneStats::packIntoMessage(unsigned char* destinationBuffer, int avai return destinationBuffer - bufferStart; // includes header! } -int OctreeSceneStats::unpackFromMessage(unsigned char* sourceBuffer, int availableBytes) { - unsigned char* startPosition = sourceBuffer; +int OctreeSceneStats::unpackFromMessage(const unsigned char* sourceBuffer, int availableBytes) { + const unsigned char* startPosition = sourceBuffer; // increment to push past the packet header - int numBytesPacketHeader = numBytesForPacketHeader(sourceBuffer); + int numBytesPacketHeader = numBytesForPacketHeader(reinterpret_cast(sourceBuffer)); sourceBuffer += numBytesPacketHeader; memcpy(&_start, sourceBuffer, sizeof(_start)); @@ -797,16 +797,16 @@ const char* OctreeSceneStats::getItemValue(Item item) { return _itemValueBuffer; } -void OctreeSceneStats::trackIncomingOctreePacket(unsigned char* messageData, ssize_t messageLength, +void OctreeSceneStats::trackIncomingOctreePacket(const QByteArray& packet, bool wasStatsPacket, int nodeClockSkewUsec) { _incomingPacket++; - _incomingBytes += messageLength; + _incomingBytes += packet.size(); if (!wasStatsPacket) { - _incomingWastedBytes += (MAX_PACKET_SIZE - messageLength); + _incomingWastedBytes += (MAX_PACKET_SIZE - packet.size()); } - int numBytesPacketHeader = numBytesForPacketHeader(messageData); - unsigned char* dataAt = messageData + numBytesPacketHeader; + int numBytesPacketHeader = numBytesForPacketHeader(packet); + const unsigned char* dataAt = reinterpret_cast(packet.data()) + numBytesPacketHeader; //VOXEL_PACKET_FLAGS flags = (*(VOXEL_PACKET_FLAGS*)(dataAt)); dataAt += sizeof(OCTREE_PACKET_FLAGS); diff --git a/libraries/octree/src/OctreeSceneStats.h b/libraries/octree/src/OctreeSceneStats.h index 833568f6f3..350470b9c1 100644 --- a/libraries/octree/src/OctreeSceneStats.h +++ b/libraries/octree/src/OctreeSceneStats.h @@ -88,7 +88,7 @@ public: int packIntoMessage(unsigned char* destinationBuffer, int availableBytes); /// Unpack the details of the statistics from a buffer typically received as a network packet - int unpackFromMessage(unsigned char* sourceBuffer, int availableBytes); + int unpackFromMessage(const unsigned char* sourceBuffer, int availableBytes); /// Indicates that a scene has been completed and the statistics are ready to be sent bool isReadyToSend() const { return _isReadyToSend; } @@ -153,8 +153,7 @@ public: unsigned long getLastFullElapsedTime() const { return _lastFullElapsed; } // Used in client implementations to track individual octree packets - void trackIncomingOctreePacket(unsigned char* messageData, ssize_t messageLength, - bool wasStatsPacket, int nodeClockSkewUsec); + void trackIncomingOctreePacket(const QByteArray& packet, bool wasStatsPacket, int nodeClockSkewUsec); unsigned int getIncomingPackets() const { return _incomingPacket; } unsigned long getIncomingBytes() const { return _incomingBytes; } diff --git a/libraries/particle-server/src/ParticleNodeData.h b/libraries/particle-server/src/ParticleNodeData.h index 1758b2e9a3..da5a9b0b71 100644 --- a/libraries/particle-server/src/ParticleNodeData.h +++ b/libraries/particle-server/src/ParticleNodeData.h @@ -19,7 +19,7 @@ public: OctreeQueryNode(), _lastDeletedParticlesSentAt(0) { }; - virtual PACKET_TYPE getMyPacketType() const { return PACKET_TYPE_PARTICLE_DATA; } + virtual PacketType getMyPacketType() const { return PacketTypeParticleData; } uint64_t getLastDeletedParticlesSentAt() const { return _lastDeletedParticlesSentAt; } void setLastDeletedParticlesSentAt(uint64_t sentAt) { _lastDeletedParticlesSentAt = sentAt; } diff --git a/libraries/particle-server/src/ParticleServer.cpp b/libraries/particle-server/src/ParticleServer.cpp index 6df12e5ff2..94bc3c3a16 100644 --- a/libraries/particle-server/src/ParticleServer.cpp +++ b/libraries/particle-server/src/ParticleServer.cpp @@ -17,7 +17,7 @@ const char* PARTICLE_SERVER_NAME = "Particle"; const char* PARTICLE_SERVER_LOGGING_TARGET_NAME = "particle-server"; const char* LOCAL_PARTICLES_PERSIST_FILE = "resources/particles.svo"; -ParticleServer::ParticleServer(const unsigned char* dataBuffer, int numBytes) : OctreeServer(dataBuffer, numBytes) { +ParticleServer::ParticleServer(const QByteArray& packet) : OctreeServer(packet) { // nothing special to do here... } @@ -47,7 +47,7 @@ void ParticleServer::particleCreated(const Particle& newParticle, Node* node) { unsigned char outputBuffer[MAX_PACKET_SIZE]; unsigned char* copyAt = outputBuffer; - int numBytesPacketHeader = populateTypeAndVersion(outputBuffer, PACKET_TYPE_PARTICLE_ADD_RESPONSE); + int numBytesPacketHeader = populatePacketHeader(reinterpret_cast(outputBuffer), PacketTypeParticleAddResponse); int packetLength = numBytesPacketHeader; copyAt += numBytesPacketHeader; @@ -102,7 +102,7 @@ int ParticleServer::sendSpecialPacket(Node* node) { hasMoreToSend = tree->encodeParticlesDeletedSince(deletedParticlesSentAt, outputBuffer, MAX_PACKET_SIZE, packetLength); - //qDebug() << "sending PACKET_TYPE_PARTICLE_ERASE packetLength:" << packetLength; + //qDebug() << "sending PacketType_PARTICLE_ERASE packetLength:" << packetLength; NodeList::getInstance()->getNodeSocket().writeDatagram((char*) outputBuffer, packetLength, node->getActiveSocket()->getAddress(), diff --git a/libraries/particle-server/src/ParticleServer.h b/libraries/particle-server/src/ParticleServer.h index 55e1b77285..4420edf947 100644 --- a/libraries/particle-server/src/ParticleServer.h +++ b/libraries/particle-server/src/ParticleServer.h @@ -20,14 +20,14 @@ class ParticleServer : public OctreeServer, public NewlyCreatedParticleHook { Q_OBJECT public: - ParticleServer(const unsigned char* dataBuffer, int numBytes); + ParticleServer(const QByteArray& packet); ~ParticleServer(); // Subclasses must implement these methods virtual OctreeQueryNode* createOctreeQueryNode(); virtual Octree* createTree(); virtual unsigned char getMyNodeType() const { return NODE_TYPE_PARTICLE_SERVER; } - virtual PACKET_TYPE getMyQueryMessageType() const { return PACKET_TYPE_PARTICLE_QUERY; } + virtual PacketType getMyQueryMessageType() const { return PacketTypeParticleQuery; } virtual const char* getMyServerName() const { return PARTICLE_SERVER_NAME; } virtual const char* getMyLoggingServerTargetName() const { return PARTICLE_SERVER_LOGGING_TARGET_NAME; } virtual const char* getMyDefaultPersistFilename() const { return LOCAL_PARTICLES_PERSIST_FILE; } diff --git a/libraries/particles/src/Particle.cpp b/libraries/particles/src/Particle.cpp index 5cf5e9248d..aef62ccf07 100644 --- a/libraries/particles/src/Particle.cpp +++ b/libraries/particles/src/Particle.cpp @@ -45,9 +45,9 @@ uint32_t Particle::getNextCreatorTokenID() { return creatorTokenID; } -void Particle::handleAddParticleResponse(unsigned char* packetData , int packetLength) { - unsigned char* dataAt = packetData; - int numBytesPacketHeader = numBytesForPacketHeader(packetData); +void Particle::handleAddParticleResponse(const QByteArray& packet) { + const unsigned char* dataAt = reinterpret_cast(packet.data()); + int numBytesPacketHeader = numBytesForPacketHeader(packet); dataAt += numBytesPacketHeader; uint32_t creatorTokenID; @@ -64,8 +64,6 @@ void Particle::handleAddParticleResponse(unsigned char* packetData , int packetL _tokenIDsToIDs[creatorTokenID] = particleID; } - - Particle::Particle(glm::vec3 position, float radius, rgbColor color, glm::vec3 velocity, glm::vec3 gravity, float damping, float lifetime, bool inHand, QString updateScript, uint32_t id) { @@ -292,12 +290,12 @@ int Particle::readParticleDataFromBuffer(const unsigned char* data, int bytesLef } -Particle Particle::fromEditPacket(unsigned char* data, int length, int& processedBytes, ParticleTree* tree) { +Particle Particle::fromEditPacket(const unsigned char* data, int length, int& processedBytes, ParticleTree* tree) { //qDebug() << "Particle::fromEditPacket() length=" << length; Particle newParticle; // id and _lastUpdated will get set here... - unsigned char* dataAt = data; + const unsigned char* dataAt = data; processedBytes = 0; // the first part of the data is our octcode... @@ -471,7 +469,7 @@ void Particle::debugDump() const { printf(" color:%d,%d,%d\n", _color[0], _color[1], _color[2]); } -bool Particle::encodeParticleEditMessageDetails(PACKET_TYPE command, ParticleID id, const ParticleProperties& properties, +bool Particle::encodeParticleEditMessageDetails(PacketType command, ParticleID id, const ParticleProperties& properties, unsigned char* bufferOut, int sizeIn, int& sizeOut) { bool success = true; // assume the best diff --git a/libraries/particles/src/Particle.h b/libraries/particles/src/Particle.h index e534c7b418..fab528595d 100644 --- a/libraries/particles/src/Particle.h +++ b/libraries/particles/src/Particle.h @@ -161,8 +161,8 @@ public: glm::vec3 gravity = DEFAULT_GRAVITY, float damping = DEFAULT_DAMPING, float lifetime = DEFAULT_LIFETIME, bool inHand = NOT_IN_HAND, QString updateScript = DEFAULT_SCRIPT, uint32_t id = NEW_PARTICLE); - /// creates an NEW particle from an PACKET_TYPE_PARTICLE_ADD_OR_EDIT edit data buffer - static Particle fromEditPacket(unsigned char* data, int length, int& processedBytes, ParticleTree* tree); + /// creates an NEW particle from an PacketType_PARTICLE_ADD_OR_EDIT edit data buffer + static Particle fromEditPacket(const unsigned char* data, int length, int& processedBytes, ParticleTree* tree); virtual ~Particle(); virtual void init(glm::vec3 position, float radius, rgbColor color, glm::vec3 velocity, @@ -235,7 +235,7 @@ public: static int expectedBytes(); static int expectedEditMessageBytes(); - static bool encodeParticleEditMessageDetails(PACKET_TYPE command, ParticleID id, const ParticleProperties& details, + static bool encodeParticleEditMessageDetails(PacketType command, ParticleID id, const ParticleProperties& details, unsigned char* bufferOut, int sizeIn, int& sizeOut); static void adjustEditPacketForClockSkew(unsigned char* codeColorBuffer, ssize_t length, int clockSkew); @@ -262,7 +262,7 @@ public: // these methods allow you to create particles, and later edit them. static uint32_t getIDfromCreatorTokenID(uint32_t creatorTokenID); static uint32_t getNextCreatorTokenID(); - static void handleAddParticleResponse(unsigned char* packetData , int packetLength); + static void handleAddParticleResponse(const QByteArray& packet); protected: static VoxelEditPacketSender* _voxelEditSender; diff --git a/libraries/particles/src/ParticleCollisionSystem.cpp b/libraries/particles/src/ParticleCollisionSystem.cpp index 7e8866e7d4..e9484e99d9 100644 --- a/libraries/particles/src/ParticleCollisionSystem.cpp +++ b/libraries/particles/src/ParticleCollisionSystem.cpp @@ -122,7 +122,7 @@ void ParticleCollisionSystem::updateCollisionWithParticles(Particle* particleA) ParticleID particleAid(particleA->getID()); propertiesA.copyFromParticle(*particleA); propertiesA.setVelocity(particleA->getVelocity() * (float)TREE_SCALE); - _packetSender->queueParticleEditMessage(PACKET_TYPE_PARTICLE_ADD_OR_EDIT, particleAid, propertiesA); + _packetSender->queueParticleEditMessage(PacketTypeParticleAddOrEdit, particleAid, propertiesA); // handle B particle particleB->setVelocity(particleB->getVelocity() + axialVelocity * (2.0f * massA / totalMass)); @@ -130,7 +130,7 @@ void ParticleCollisionSystem::updateCollisionWithParticles(Particle* particleA) ParticleID particleBid(particleB->getID()); propertiesB.copyFromParticle(*particleB); propertiesB.setVelocity(particleB->getVelocity() * (float)TREE_SCALE); - _packetSender->queueParticleEditMessage(PACKET_TYPE_PARTICLE_ADD_OR_EDIT, particleBid, propertiesB); + _packetSender->queueParticleEditMessage(PacketTypeParticleAddOrEdit, particleBid, propertiesB); _packetSender->releaseQueuedMessages(); @@ -264,7 +264,7 @@ void ParticleCollisionSystem::applyHardCollision(Particle* particle, float elast properties.copyFromParticle(*particle); properties.setPosition(position * (float)TREE_SCALE); properties.setVelocity(velocity * (float)TREE_SCALE); - _packetSender->queueParticleEditMessage(PACKET_TYPE_PARTICLE_ADD_OR_EDIT, particleID, properties); + _packetSender->queueParticleEditMessage(PacketTypeParticleAddOrEdit, particleID, properties); // change the local particle too... particle->setPosition(position); diff --git a/libraries/particles/src/ParticleEditPacketSender.cpp b/libraries/particles/src/ParticleEditPacketSender.cpp index 3206a0d200..f06b19aa2d 100644 --- a/libraries/particles/src/ParticleEditPacketSender.cpp +++ b/libraries/particles/src/ParticleEditPacketSender.cpp @@ -16,7 +16,7 @@ #include "Particle.h" -void ParticleEditPacketSender::sendEditParticleMessage(PACKET_TYPE type, ParticleID particleID, const ParticleProperties& properties) { +void ParticleEditPacketSender::sendEditParticleMessage(PacketType type, ParticleID particleID, const ParticleProperties& properties) { // allows app to disable sending if for example voxels have been disabled if (!_shouldSend) { return; // bail early @@ -42,7 +42,7 @@ void ParticleEditPacketSender::adjustEditPacketForClockSkew(unsigned char* codeC } -void ParticleEditPacketSender::queueParticleEditMessage(PACKET_TYPE type, ParticleID particleID, +void ParticleEditPacketSender::queueParticleEditMessage(PacketType type, ParticleID particleID, const ParticleProperties& properties) { if (!_shouldSend) { return; // bail early diff --git a/libraries/particles/src/ParticleEditPacketSender.h b/libraries/particles/src/ParticleEditPacketSender.h index 51f0fd9b96..f406ba625a 100644 --- a/libraries/particles/src/ParticleEditPacketSender.h +++ b/libraries/particles/src/ParticleEditPacketSender.h @@ -20,13 +20,13 @@ class ParticleEditPacketSender : public OctreeEditPacketSender { public: /// Send particle add message immediately /// NOTE: ParticleProperties assumes that all distances are in meter units - void sendEditParticleMessage(PACKET_TYPE type, ParticleID particleID, const ParticleProperties& properties); + void sendEditParticleMessage(PacketType type, ParticleID particleID, const ParticleProperties& properties); /// Queues an array of several voxel edit messages. Will potentially send a pending multi-command packet. Determines /// which voxel-server node or nodes the packet should be sent to. Can be called even before voxel servers are known, in /// which case up to MaxPendingMessages will be buffered and processed when voxel servers are known. /// NOTE: ParticleProperties assumes that all distances are in meter units - void queueParticleEditMessage(PACKET_TYPE type, ParticleID particleID, const ParticleProperties& properties); + void queueParticleEditMessage(PacketType type, ParticleID particleID, const ParticleProperties& properties); // My server type is the particle server virtual unsigned char getMyNodeType() const { return NODE_TYPE_PARTICLE_SERVER; } diff --git a/libraries/particles/src/ParticleTree.cpp b/libraries/particles/src/ParticleTree.cpp index cd59e0e3a7..0c90a03573 100644 --- a/libraries/particles/src/ParticleTree.cpp +++ b/libraries/particles/src/ParticleTree.cpp @@ -19,14 +19,15 @@ ParticleTreeElement* ParticleTree::createNewElement(unsigned char * octalCode) { return newElement; } -bool ParticleTree::handlesEditPacketType(PACKET_TYPE packetType) const { +bool ParticleTree::handlesEditPacketType(PacketType packetType) const { // we handle these types of "edit" packets switch (packetType) { - case PACKET_TYPE_PARTICLE_ADD_OR_EDIT: - case PACKET_TYPE_PARTICLE_ERASE: + case PacketTypeParticleAddOrEdit: + case PacketTypeParticleErase: return true; + default: + return false; } - return false; } class FindAndDeleteParticlesArgs { @@ -207,29 +208,30 @@ const Particle* ParticleTree::findParticleByID(uint32_t id, bool alreadyLocked) } -int ParticleTree::processEditPacketData(PACKET_TYPE packetType, unsigned char* packetData, int packetLength, - unsigned char* editData, int maxLength, Node* senderNode) { +int ParticleTree::processEditPacketData(PacketType packetType, const unsigned char* packetData, int packetLength, + const unsigned char* editData, int maxLength, Node* senderNode) { int processedBytes = 0; // we handle these types of "edit" packets switch (packetType) { - case PACKET_TYPE_PARTICLE_ADD_OR_EDIT: { - //qDebug() << " got PACKET_TYPE_PARTICLE_ADD_OR_EDIT... "; + case PacketTypeParticleAddOrEdit: { + //qDebug() << " got PacketType_PARTICLE_ADD_OR_EDIT... "; Particle newParticle = Particle::fromEditPacket(editData, maxLength, processedBytes, this); storeParticle(newParticle, senderNode); if (newParticle.isNewlyCreated()) { notifyNewlyCreatedParticle(newParticle, senderNode); } - //qDebug() << " DONE... PACKET_TYPE_PARTICLE_ADD_OR_EDIT... "; - } break; + //qDebug() << " DONE... PacketType_PARTICLE_ADD_OR_EDIT... "; + return processedBytes; + } - // TODO: wire in support here for server to get PACKET_TYPE_PARTICLE_ERASE messages - // instead of using PACKET_TYPE_PARTICLE_ADD_OR_EDIT messages to delete particles - case PACKET_TYPE_PARTICLE_ERASE: { - processedBytes = 0; - } break; + // TODO: wire in support here for server to get PacketType_PARTICLE_ERASE messages + // instead of using PacketType_PARTICLE_ADD_OR_EDIT messages to delete particles + case PacketTypeParticleErase: + return 0; + default: + return 0; } - return processedBytes; } void ParticleTree::notifyNewlyCreatedParticle(const Particle& newParticle, Node* senderNode) { @@ -331,7 +333,7 @@ bool ParticleTree::encodeParticlesDeletedSince(uint64_t& sinceTime, unsigned cha bool hasMoreToSend = true; unsigned char* copyAt = outputBuffer; - size_t numBytesPacketHeader = populateTypeAndVersion(outputBuffer, PACKET_TYPE_PARTICLE_ERASE); + size_t numBytesPacketHeader = populatePacketHeader(reinterpret_cast(outputBuffer), PacketTypeParticleErase); copyAt += numBytesPacketHeader; outputLength = numBytesPacketHeader; @@ -424,7 +426,7 @@ void ParticleTree::processEraseMessage(const QByteArray& dataByteArray, const Hi const unsigned char* dataAt = packetData; size_t packetLength = dataByteArray.size(); - size_t numBytesPacketHeader = numBytesForPacketHeader(packetData); + size_t numBytesPacketHeader = numBytesForPacketHeader(dataByteArray); size_t processedBytes = numBytesPacketHeader; dataAt += numBytesPacketHeader; diff --git a/libraries/particles/src/ParticleTree.h b/libraries/particles/src/ParticleTree.h index 2b7efbbe78..c89bd01b3b 100644 --- a/libraries/particles/src/ParticleTree.h +++ b/libraries/particles/src/ParticleTree.h @@ -32,10 +32,10 @@ public: // These methods will allow the OctreeServer to send your tree inbound edit packets of your // own definition. Implement these to allow your octree based server to support editing virtual bool getWantSVOfileVersions() const { return true; } - virtual PACKET_TYPE expectedDataPacketType() const { return PACKET_TYPE_PARTICLE_DATA; } - virtual bool handlesEditPacketType(PACKET_TYPE packetType) const; - virtual int processEditPacketData(PACKET_TYPE packetType, unsigned char* packetData, int packetLength, - unsigned char* editData, int maxLength, Node* senderNode); + virtual PacketType expectedDataPacketType() const { return PacketTypeParticleData; } + virtual bool handlesEditPacketType(PacketType packetType) const; + virtual int processEditPacketData(PacketType packetType, const unsigned char* packetData, int packetLength, + const unsigned char* editData, int maxLength, Node* senderNode); virtual void update(); diff --git a/libraries/particles/src/ParticlesScriptingInterface.cpp b/libraries/particles/src/ParticlesScriptingInterface.cpp index 14388b6ac4..987fdf789c 100644 --- a/libraries/particles/src/ParticlesScriptingInterface.cpp +++ b/libraries/particles/src/ParticlesScriptingInterface.cpp @@ -16,7 +16,7 @@ ParticlesScriptingInterface::ParticlesScriptingInterface() : } -void ParticlesScriptingInterface::queueParticleMessage(PACKET_TYPE packetType, +void ParticlesScriptingInterface::queueParticleMessage(PacketType packetType, ParticleID particleID, const ParticleProperties& properties) { getParticlePacketSender()->queueParticleEditMessage(packetType, particleID, properties); } @@ -29,7 +29,7 @@ ParticleID ParticlesScriptingInterface::addParticle(const ParticleProperties& pr ParticleID id(NEW_PARTICLE, creatorTokenID, false ); // queue the packet - queueParticleMessage(PACKET_TYPE_PARTICLE_ADD_OR_EDIT, id, properties); + queueParticleMessage(PacketTypeParticleAddOrEdit, id, properties); return id; } @@ -70,13 +70,13 @@ void ParticlesScriptingInterface::editParticle(ParticleID particleID, const Part qDebug() << "ParticlesScriptingInterface::editParticle()... properties.getInHand()=" << properties.getInHand(); } } - queueParticleMessage(PACKET_TYPE_PARTICLE_ADD_OR_EDIT, particleID, properties); + queueParticleMessage(PacketTypeParticleAddOrEdit, particleID, properties); } -// TODO: This deleteParticle() method uses the PACKET_TYPE_PARTICLE_ADD_OR_EDIT message to send +// TODO: This deleteParticle() method uses the PacketType_PARTICLE_ADD_OR_EDIT message to send // a changed particle with a shouldDie() property set to true. This works and is currently the only -// way to tell the particle server to delete a particle. But we should change this to use the PACKET_TYPE_PARTICLE_ERASE +// way to tell the particle server to delete a particle. But we should change this to use the PacketType_PARTICLE_ERASE // message which takes a list of particle id's to delete. void ParticlesScriptingInterface::deleteParticle(ParticleID particleID) { @@ -99,7 +99,7 @@ void ParticlesScriptingInterface::deleteParticle(ParticleID particleID) { particleID.isKnownID = true; //qDebug() << "ParticlesScriptingInterface::deleteParticle(), queueParticleMessage......"; - queueParticleMessage(PACKET_TYPE_PARTICLE_ADD_OR_EDIT, particleID, properties); + queueParticleMessage(PacketTypeParticleAddOrEdit, particleID, properties); } ParticleID ParticlesScriptingInterface::findClosestParticle(const glm::vec3& center, float radius) const { diff --git a/libraries/particles/src/ParticlesScriptingInterface.h b/libraries/particles/src/ParticlesScriptingInterface.h index d61f8289f4..624ce8a7b1 100644 --- a/libraries/particles/src/ParticlesScriptingInterface.h +++ b/libraries/particles/src/ParticlesScriptingInterface.h @@ -34,7 +34,7 @@ public slots: ParticleID findClosestParticle(const glm::vec3& center, float radius) const; private: - void queueParticleMessage(PACKET_TYPE packetType, ParticleID particleID, const ParticleProperties& properties); + void queueParticleMessage(PacketType packetType, ParticleID particleID, const ParticleProperties& properties); uint32_t _nextCreatorTokenID; ParticleTree* _particleTree; diff --git a/libraries/script-engine/src/ScriptEngine.cpp b/libraries/script-engine/src/ScriptEngine.cpp index f77b428764..f511299fcd 100644 --- a/libraries/script-engine/src/ScriptEngine.cpp +++ b/libraries/script-engine/src/ScriptEngine.cpp @@ -236,21 +236,19 @@ void ScriptEngine::run() { } if (_isAvatar && _avatarData) { - static unsigned char avatarPacket[MAX_PACKET_SIZE]; - static int numAvatarHeaderBytes = 0; + static QByteArray avatarPacket; + int numAvatarHeaderBytes = 0; - if (numAvatarHeaderBytes == 0) { + if (avatarPacket.size() == 0) { // pack the avatar header bytes the first time // unlike the _avatar.getBroadcastData these won't change - numAvatarHeaderBytes = populateTypeAndVersion(avatarPacket, PACKET_TYPE_HEAD_DATA); - - // pack the owner UUID for this script - numAvatarHeaderBytes += NodeList::getInstance()->packOwnerUUID(avatarPacket); + numAvatarHeaderBytes = populatePacketHeader(avatarPacket, PacketTypeAvatarData); } - int numAvatarPacketBytes = _avatarData->getBroadcastData(avatarPacket + numAvatarHeaderBytes) + numAvatarHeaderBytes; + avatarPacket.resize(numAvatarHeaderBytes); + avatarPacket.append(_avatarData->toByteArray()); - nodeList->broadcastToNodes(avatarPacket, numAvatarPacketBytes, QSet() << NODE_TYPE_AVATAR_MIXER); + nodeList->broadcastToNodes(avatarPacket, QSet() << NODE_TYPE_AVATAR_MIXER); } if (willSendVisualDataCallBack) { diff --git a/libraries/shared/src/Assignment.cpp b/libraries/shared/src/Assignment.cpp index 8e67e7a178..0040fd47a3 100644 --- a/libraries/shared/src/Assignment.cpp +++ b/libraries/shared/src/Assignment.cpp @@ -48,19 +48,18 @@ Assignment::Assignment() : _type(Assignment::AllTypes), _location(Assignment::LocalLocation), _numberOfInstances(1), - _payload(), - _numPayloadBytes(0) + _payload() { setPool(NULL); } -Assignment::Assignment(Assignment::Command command, Assignment::Type type, const char* pool, Assignment::Location location) : +Assignment::Assignment(Assignment::Command command, Assignment::Type type, const QString& pool, Assignment::Location location) : _command(command), _type(type), + _pool(pool), _location(location), _numberOfInstances(1), - _payload(), - _numPayloadBytes(0) + _payload() { if (_command == Assignment::CreateCommand) { // this is a newly created assignment, generate a random UUID @@ -70,45 +69,33 @@ Assignment::Assignment(Assignment::Command command, Assignment::Type type, const setPool(pool); } -Assignment::Assignment(const unsigned char* dataBuffer, int numBytes) : +Assignment::Assignment(const QByteArray& packet) : _location(GlobalLocation), _numberOfInstances(1), - _payload(), - _numPayloadBytes(0) + _payload() { - int numBytesRead = 0; + PacketType packetType = packetTypeForPacket(packet); - if (dataBuffer[0] == PACKET_TYPE_REQUEST_ASSIGNMENT) { + if (packetType == PacketTypeRequestAssignment) { _command = Assignment::RequestCommand; - } else if (dataBuffer[0] == PACKET_TYPE_CREATE_ASSIGNMENT) { + } else if (packetType == PacketTypeCreateAssignment) { _command = Assignment::CreateCommand; - } else if (dataBuffer[0] == PACKET_TYPE_DEPLOY_ASSIGNMENT) { - _command = Assignment::DeployCommand; } - numBytesRead += numBytesForPacketHeader(dataBuffer); + QDataStream packetStream(packet); + packetStream.skipRawData(numBytesForPacketHeader(packet)); - memcpy(&_type, dataBuffer + numBytesRead, sizeof(Assignment::Type)); - numBytesRead += sizeof(Assignment::Type); + packetStream.readRawData(reinterpret_cast(&_type), sizeof(Assignment::Type)); if (_command != Assignment::RequestCommand) { // read the GUID for this assignment - _uuid = QUuid::fromRfc4122(QByteArray((const char*) dataBuffer + numBytesRead, NUM_BYTES_RFC4122_UUID)); - numBytesRead += NUM_BYTES_RFC4122_UUID; + packetStream >> _uuid; } - if (dataBuffer[numBytesRead] != '\0') { - // read the pool from the data buffer - setPool((const char*) dataBuffer + numBytesRead); - numBytesRead += strlen(_pool) + sizeof('\0'); - } else { - // skip past the null pool and null out our pool - setPool(NULL); - numBytesRead++; - } + packetStream >> _pool; - if (numBytes > numBytesRead) { - setPayload(dataBuffer + numBytesRead, numBytes - numBytesRead); + if (!packetStream.atEnd()) { + _payload = packet.mid(packetStream.device()->pos()); } } @@ -124,10 +111,9 @@ Assignment::Assignment(const Assignment& otherAssignment) { _command = otherAssignment._command; _type = otherAssignment._type; _location = otherAssignment._location; - setPool(otherAssignment._pool); + _pool = otherAssignment._pool; _numberOfInstances = otherAssignment._numberOfInstances; - - setPayload(otherAssignment._payload, otherAssignment._numPayloadBytes); + _payload = otherAssignment._payload; } Assignment& Assignment::operator=(const Assignment& rhsAssignment) { @@ -143,42 +129,10 @@ void Assignment::swap(Assignment& otherAssignment) { swap(_command, otherAssignment._command); swap(_type, otherAssignment._type); swap(_location, otherAssignment._location); - - for (int i = 0; i < sizeof(_pool); i++) { - swap(_pool[i], otherAssignment._pool[i]); - } + swap(_pool, otherAssignment._pool); swap(_numberOfInstances, otherAssignment._numberOfInstances); - - for (int i = 0; i < MAX_PAYLOAD_BYTES; i++) { - swap(_payload[i], otherAssignment._payload[i]); - } - - swap(_numPayloadBytes, otherAssignment._numPayloadBytes); -} - -void Assignment::setPayload(const uchar* payload, int numBytes) { - - if (numBytes > MAX_PAYLOAD_BYTES) { - qDebug("Set payload called with number of bytes greater than maximum (%d). Will only transfer %d bytes.", - MAX_PAYLOAD_BYTES, - MAX_PAYLOAD_BYTES); - - _numPayloadBytes = 1024; - } else { - _numPayloadBytes = numBytes; - } - - memset(_payload, 0, MAX_PAYLOAD_BYTES); - memcpy(_payload, payload, _numPayloadBytes); -} - -void Assignment::setPool(const char* pool) { - memset(_pool, '\0', sizeof(_pool)); - - if (pool) { - strcpy(_pool, pool); - } + swap(_payload, otherAssignment._payload); } const char* Assignment::getTypeName() const { @@ -200,38 +154,21 @@ const char* Assignment::getTypeName() const { } } -int Assignment::packToBuffer(unsigned char* buffer) { - int numPackedBytes = 0; - - memcpy(buffer + numPackedBytes, &_type, sizeof(_type)); - numPackedBytes += sizeof(_type); - - // pack the UUID for this assignment, if this is an assignment create or deploy - if (_command != Assignment::RequestCommand) { - memcpy(buffer + numPackedBytes, _uuid.toRfc4122().constData(), NUM_BYTES_RFC4122_UUID); - numPackedBytes += NUM_BYTES_RFC4122_UUID; - } - - if (hasPool()) { - // pack the pool for this assignment, it exists - int numBytesNullTerminatedPool = strlen(_pool) + sizeof('\0'); - memcpy(buffer + numPackedBytes, _pool, numBytesNullTerminatedPool); - numPackedBytes += numBytesNullTerminatedPool; - } else { - // otherwise pack the null character - buffer[numPackedBytes++] = '\0'; - } - - if (_numPayloadBytes) { - memcpy(buffer + numPackedBytes, _payload, _numPayloadBytes); - numPackedBytes += _numPayloadBytes; - } - - return numPackedBytes; -} - QDebug operator<<(QDebug debug, const Assignment &assignment) { debug.nospace() << "UUID: " << assignment.getUUID().toString().toStdString().c_str() << ", Type: " << assignment.getType(); return debug.nospace(); } + +QDataStream& operator<<(QDataStream &out, const Assignment& assignment) { + out << (char) assignment._type; + + // pack the UUID for this assignment, if this is an assignment create or deploy + if (assignment._command != Assignment::RequestCommand) { + out << assignment._uuid; + } + + out << assignment._pool << assignment._payload; + + return out; +} diff --git a/libraries/shared/src/Assignment.h b/libraries/shared/src/Assignment.h index 3f73748251..2cf026682a 100644 --- a/libraries/shared/src/Assignment.h +++ b/libraries/shared/src/Assignment.h @@ -22,6 +22,8 @@ const int MAX_PAYLOAD_BYTES = 1024; const int MAX_ASSIGNMENT_POOL_BYTES = 64 + sizeof('\0'); +const QString emptyPool = QString(); + /// Holds information used for request, creation, and deployment of assignments class Assignment : public NodeData { Q_OBJECT @@ -53,7 +55,7 @@ public: Assignment(); Assignment(Assignment::Command command, Assignment::Type type, - const char* pool = NULL, + const QString& pool = emptyPool, Assignment::Location location = Assignment::LocalLocation); Assignment(const Assignment& otherAssignment); Assignment& operator=(const Assignment &rhsAssignment); @@ -63,7 +65,7 @@ public: /// Constructs an Assignment from the data in the buffer /// \param dataBuffer the source buffer to un-pack the assignment from /// \param numBytes the number of bytes left to read in the source buffer - Assignment(const unsigned char* dataBuffer, int numBytes); + Assignment(const QByteArray& packet); void setUUID(const QUuid& uuid) { _uuid = uuid; } const QUuid& getUUID() const { return _uuid; } @@ -73,13 +75,11 @@ public: Assignment::Type getType() const { return _type; } Assignment::Location getLocation() const { return _location; } - uchar* getPayload() { return _payload; } - int getNumPayloadBytes() const { return _numPayloadBytes; } - void setPayload(const uchar *payload, int numBytes); + const QByteArray& getPayload() const { return _payload; } + void setPayload(const QByteArray& payload) { _payload = payload; } - void setPool(const char* pool); - const char* getPool() const { return _pool; } - bool hasPool() const { return (bool) strlen(_pool); } + void setPool(const QString& pool) { _pool = pool; }; + const QString& getPool() const { return _pool; } int getNumberOfInstances() const { return _numberOfInstances; } void setNumberOfInstances(int numberOfInstances) { _numberOfInstances = numberOfInstances; } @@ -87,27 +87,20 @@ public: const char* getTypeName() const; - /// Packs the assignment to the passed buffer - /// \param buffer the buffer in which to pack the assignment - /// \return number of bytes packed into buffer - int packToBuffer(unsigned char* buffer); - // implement parseData to return 0 so we can be a subclass of NodeData - int parseData(unsigned char* sourceBuffer, int numBytes) { return 0; } + int parseData(const QByteArray& packet) { return 0; } friend QDebug operator<<(QDebug debug, const Assignment& assignment); friend QDataStream& operator<<(QDataStream &out, const Assignment& assignment); - friend QDataStream& operator>>(QDataStream &in, Assignment& assignment); protected: QUuid _uuid; /// the 16 byte UUID for this assignment Assignment::Command _command; /// the command for this assignment (Create, Deploy, Request) Assignment::Type _type; /// the type of the assignment, defines what the assignee will do - char _pool[MAX_ASSIGNMENT_POOL_BYTES]; /// the destination pool for this assignment + QString _pool; /// the destination pool for this assignment Assignment::Location _location; /// the location of the assignment, allows a domain to preferentially use local ACs int _numberOfInstances; /// the number of instances of this assignment - uchar _payload[MAX_PAYLOAD_BYTES]; /// an optional payload attached to this assignment, a maximum for 1024 bytes will be packed - int _numPayloadBytes; /// number of bytes in the payload, up to a maximum of 1024 + QByteArray _payload; /// an optional payload attached to this assignment, a maximum for 1024 bytes will be packed }; #endif /* defined(__hifi__Assignment__) */ diff --git a/libraries/shared/src/DataServerClient.cpp b/libraries/shared/src/DataServerClient.cpp index 787e5ab8e2..fd003aa3bb 100644 --- a/libraries/shared/src/DataServerClient.cpp +++ b/libraries/shared/src/DataServerClient.cpp @@ -30,39 +30,18 @@ const HifiSockAddr& DataServerClient::dataServerSockAddr() { } void DataServerClient::putValueForKeyAndUserString(const QString& key, const QString& value, const QString& userString) { - unsigned char putPacket[MAX_PACKET_SIZE]; + // setup the header for this packet and push packetStream to desired spot + QByteArray putPacket = byteArrayWithPopluatedHeader(PacketTypeDataServerPut); + QDataStream packetStream(&putPacket, QIODevice::Append); - // setup the header for this packet - int numPacketBytes = populateTypeAndVersion(putPacket, PACKET_TYPE_DATA_SERVER_PUT); - - // pack the sequence number - memcpy(putPacket + numPacketBytes, &_sequenceNumber, sizeof(_sequenceNumber)); - numPacketBytes += sizeof(_sequenceNumber); - - // pack the client UUID, null terminated - memcpy(putPacket + numPacketBytes, qPrintable(userString), userString.size()); - numPacketBytes += userString.size(); - putPacket[numPacketBytes++] = '\0'; - - // pack a 1 to designate that we are putting a single value - putPacket[numPacketBytes++] = 1; - - // pack the key, null terminated - strcpy((char*) putPacket + numPacketBytes, qPrintable(key)); - numPacketBytes += key.size(); - putPacket[numPacketBytes++] = '\0'; - - // pack the value, null terminated - strcpy((char*) putPacket + numPacketBytes, qPrintable(value)); - numPacketBytes += value.size(); - putPacket[numPacketBytes++] = '\0'; + // pack our data for the put packet + packetStream << _sequenceNumber << userString << key << value; // add the putPacket to our vector of unconfirmed packets, will be deleted once put is confirmed - _unmatchedPackets.insert(_sequenceNumber, QByteArray((char*) putPacket, numPacketBytes)); + _unmatchedPackets.insert(_sequenceNumber, putPacket); // send this put request to the data server - NodeList::getInstance()->getNodeSocket().writeDatagram((char*) putPacket, numPacketBytes, - dataServerSockAddr().getAddress(), + NodeList::getInstance()->getNodeSocket().writeDatagram(putPacket, dataServerSockAddr().getAddress(), dataServerSockAddr().getPort()); // push the sequence number forwards @@ -87,38 +66,19 @@ void DataServerClient::getValuesForKeysAndUUID(const QStringList& keys, const QU void DataServerClient::getValuesForKeysAndUserString(const QStringList& keys, const QString& userString, DataServerCallbackObject* callbackObject) { if (!userString.isEmpty() && keys.size() <= UCHAR_MAX) { - unsigned char getPacket[MAX_PACKET_SIZE]; + QByteArray getPacket = byteArrayWithPopluatedHeader(PacketTypeDataServerGet); + QDataStream packetStream(&getPacket, QIODevice::Append); - // setup the header for this packet - int numPacketBytes = populateTypeAndVersion(getPacket, PACKET_TYPE_DATA_SERVER_GET); + // pack our data for the getPacket + packetStream << _sequenceNumber << userString << keys.join(MULTI_KEY_VALUE_SEPARATOR); - // pack the sequence number - memcpy(getPacket + numPacketBytes, &_sequenceNumber, sizeof(_sequenceNumber)); - numPacketBytes += sizeof(_sequenceNumber); - - // pack the user string (could be username or UUID string), null-terminate - memcpy(getPacket + numPacketBytes, qPrintable(userString), userString.size()); - numPacketBytes += userString.size(); - getPacket[numPacketBytes++] = '\0'; - - // pack one byte to designate the number of keys - getPacket[numPacketBytes++] = keys.size(); - - QString keyString = keys.join(MULTI_KEY_VALUE_SEPARATOR); - - // pack the key string, null terminated - strcpy((char*) getPacket + numPacketBytes, keyString.toLocal8Bit().constData()); - numPacketBytes += keyString.size() + sizeof('\0'); - // add the getPacket to our map of unconfirmed packets, will be deleted once we get a response from the nameserver - _unmatchedPackets.insert(_sequenceNumber, QByteArray((char*) getPacket, numPacketBytes)); + _unmatchedPackets.insert(_sequenceNumber, getPacket); _callbackObjects.insert(_sequenceNumber, callbackObject); // send the get to the data server - NodeList::getInstance()->getNodeSocket().writeDatagram((char*) getPacket, numPacketBytes, - dataServerSockAddr().getAddress(), + NodeList::getInstance()->getNodeSocket().writeDatagram(getPacket, dataServerSockAddr().getAddress(), dataServerSockAddr().getPort()); - _sequenceNumber++; } } @@ -128,49 +88,47 @@ void DataServerClient::getValueForKeyAndUserString(const QString& key, const QSt getValuesForKeysAndUserString(QStringList(key), userString, callbackObject); } -void DataServerClient::processConfirmFromDataServer(unsigned char* packetData) { - removeMatchedPacketFromMap(packetData); +void DataServerClient::processConfirmFromDataServer(const QByteArray& packet) { + removeMatchedPacketFromMap(packet); } -void DataServerClient::processSendFromDataServer(unsigned char* packetData, int numPacketBytes) { +void DataServerClient::processSendFromDataServer(const QByteArray& packet) { // pull the user string from the packet so we know who to associate this with - int numHeaderBytes = numBytesForPacketHeader(packetData); + QDataStream packetStream(packet); + packetStream.skipRawData(numBytesForPacketHeader(packet)); - quint8 sequenceNumber = *(packetData + numHeaderBytes); + quint8 sequenceNumber = 0; + packetStream >> sequenceNumber; if (_callbackObjects.find(sequenceNumber) != _callbackObjects.end()) { // remove the packet from our two maps, it's matched DataServerCallbackObject* callbackObject = _callbackObjects.take(sequenceNumber); _unmatchedPackets.remove(sequenceNumber); - char* userStringPosition = (char*) packetData + numHeaderBytes + sizeof(sequenceNumber); - QString userString(userStringPosition); + QString userString, keyListString, valueListString; - char* keysPosition = userStringPosition + userString.size() + sizeof('\0') + sizeof(unsigned char); - char* valuesPosition = keysPosition + strlen(keysPosition) + sizeof('\0'); + packetStream >> userString >> keyListString >> valueListString; - QStringList keyList = QString(keysPosition).split(MULTI_KEY_VALUE_SEPARATOR); - QStringList valueList = QString(valuesPosition).split(MULTI_KEY_VALUE_SEPARATOR); - - callbackObject->processDataServerResponse(userString, keyList, valueList); + callbackObject->processDataServerResponse(userString, keyListString.split(MULTI_KEY_VALUE_SEPARATOR), + valueListString.split(MULTI_KEY_VALUE_SEPARATOR)); } } -void DataServerClient::processMessageFromDataServer(unsigned char* packetData, int numPacketBytes) { - switch (packetData[0]) { - case PACKET_TYPE_DATA_SERVER_SEND: - processSendFromDataServer(packetData, numPacketBytes); +void DataServerClient::processMessageFromDataServer(const QByteArray& packet) { + switch (packetTypeForPacket(packet)) { + case PacketTypeDataServerSend: + processSendFromDataServer(packet); break; - case PACKET_TYPE_DATA_SERVER_CONFIRM: - processConfirmFromDataServer(packetData); + case PacketTypeDataServerConfirm: + processConfirmFromDataServer(packet); break; default: break; } } -void DataServerClient::removeMatchedPacketFromMap(unsigned char* packetData) { - quint8 sequenceNumber = *(packetData + numBytesForPacketHeader(packetData)); +void DataServerClient::removeMatchedPacketFromMap(const QByteArray& packet) { + quint8 sequenceNumber = packet[numBytesForPacketHeader(packet)]; // attempt to remove a packet with this sequence number from the QMap of unmatched packets _unmatchedPackets.remove(sequenceNumber); diff --git a/libraries/shared/src/DataServerClient.h b/libraries/shared/src/DataServerClient.h index 78826022ae..0360576645 100644 --- a/libraries/shared/src/DataServerClient.h +++ b/libraries/shared/src/DataServerClient.h @@ -37,13 +37,13 @@ public: static void getValuesForKeysAndUserString(const QStringList& keys, const QString& userString, DataServerCallbackObject* callbackObject); - static void processMessageFromDataServer(unsigned char* packetData, int numPacketBytes); + static void processMessageFromDataServer(const QByteArray& packet); static void resendUnmatchedPackets(); private: - static void processConfirmFromDataServer(unsigned char* packetData); - static void processSendFromDataServer(unsigned char* packetData, int numPacketBytes); - static void removeMatchedPacketFromMap(unsigned char* packetData); + static void processConfirmFromDataServer(const QByteArray& packet); + static void processSendFromDataServer(const QByteArray& packet); + static void removeMatchedPacketFromMap(const QByteArray& packet); static QMap _unmatchedPackets; static QMap _callbackObjects; diff --git a/libraries/shared/src/HifiSockAddr.cpp b/libraries/shared/src/HifiSockAddr.cpp index 4c9772b1c8..a658c75a44 100644 --- a/libraries/shared/src/HifiSockAddr.cpp +++ b/libraries/shared/src/HifiSockAddr.cpp @@ -59,31 +59,25 @@ void HifiSockAddr::swap(HifiSockAddr& otherSockAddr) { swap(_port, otherSockAddr._port); } -int HifiSockAddr::packSockAddr(unsigned char* packetData, const HifiSockAddr& packSockAddr) { - quint32 addressToPack = packSockAddr._address.isNull() ? 0 : packSockAddr._address.toIPv4Address(); - memcpy(packetData, &addressToPack, sizeof(addressToPack)); - memcpy(packetData + sizeof(addressToPack), &packSockAddr._port, sizeof(packSockAddr._port)); - - return sizeof(addressToPack) + sizeof(packSockAddr._port); -} - -int HifiSockAddr::unpackSockAddr(const unsigned char* packetData, HifiSockAddr& unpackDestSockAddr) { - quint32* address = (quint32*) packetData; - unpackDestSockAddr._address = *address == 0 ? QHostAddress() : QHostAddress(*address); - unpackDestSockAddr._port = *((quint16*) (packetData + sizeof(quint32))); - - return sizeof(quint32) + sizeof(quint16); -} - -bool HifiSockAddr::operator==(const HifiSockAddr &rhsSockAddr) const { +bool HifiSockAddr::operator==(const HifiSockAddr& rhsSockAddr) const { return _address == rhsSockAddr._address && _port == rhsSockAddr._port; } -QDebug operator<<(QDebug debug, const HifiSockAddr &hifiSockAddr) { - debug.nospace() << hifiSockAddr._address.toString().toLocal8Bit().constData() << ":" << hifiSockAddr._port; +QDebug operator<<(QDebug debug, const HifiSockAddr& sockAddr) { + debug.nospace() << sockAddr._address.toString().toLocal8Bit().constData() << ":" << sockAddr._port; return debug.space(); } +QDataStream& operator<<(QDataStream& dataStream, const HifiSockAddr& sockAddr) { + dataStream << sockAddr._address << sockAddr._port; + return dataStream; +} + +QDataStream& operator>>(QDataStream& dataStream, HifiSockAddr& sockAddr) { + dataStream >> sockAddr._address >> sockAddr._port; + return dataStream; +} + quint32 getHostOrderLocalAddress() { static int localAddress = 0; diff --git a/libraries/shared/src/HifiSockAddr.h b/libraries/shared/src/HifiSockAddr.h index f11492805f..e8f928c36d 100644 --- a/libraries/shared/src/HifiSockAddr.h +++ b/libraries/shared/src/HifiSockAddr.h @@ -37,7 +37,9 @@ public: static int packSockAddr(unsigned char* packetData, const HifiSockAddr& packSockAddr); static int unpackSockAddr(const unsigned char* packetData, HifiSockAddr& unpackDestSockAddr); - friend QDebug operator<<(QDebug debug, const HifiSockAddr &hifiSockAddr); + friend QDebug operator<<(QDebug debug, const HifiSockAddr& sockAddr); + friend QDataStream& operator<<(QDataStream& dataStream, const HifiSockAddr& sockAddr); + friend QDataStream& operator>>(QDataStream& dataStream, HifiSockAddr& sockAddr); private: QHostAddress _address; quint16 _port; diff --git a/libraries/shared/src/NetworkPacket.cpp b/libraries/shared/src/NetworkPacket.cpp index 768e82cab3..aacd95dbbf 100644 --- a/libraries/shared/src/NetworkPacket.cpp +++ b/libraries/shared/src/NetworkPacket.cpp @@ -14,49 +14,38 @@ #include "NetworkPacket.h" -NetworkPacket::NetworkPacket() { - _packetLength = 0; -} - -NetworkPacket::~NetworkPacket() { - // nothing to do -} - -void NetworkPacket::copyContents(const HifiSockAddr& sockAddr, const unsigned char* packetData, ssize_t packetLength) { - _packetLength = 0; - if (packetLength >=0 && packetLength <= MAX_PACKET_SIZE) { +void NetworkPacket::copyContents(const HifiSockAddr& sockAddr, const QByteArray& packet) { + if (packet.size() && packet.size() <= MAX_PACKET_SIZE) { _sockAddr = sockAddr; - _packetLength = packetLength; - memcpy(&_packetData[0], packetData, packetLength); + _byteArray = packet; } else { - qDebug(">>> NetworkPacket::copyContents() unexpected length=%lu",packetLength); + qDebug(">>> NetworkPacket::copyContents() unexpected length = %d", packet.size()); } } NetworkPacket::NetworkPacket(const NetworkPacket& packet) { - copyContents(packet.getSockAddr(), packet.getData(), packet.getLength()); + copyContents(packet.getSockAddr(), packet.getByteArray()); } -NetworkPacket::NetworkPacket(const HifiSockAddr& sockAddr, unsigned char* packetData, ssize_t packetLength) { - copyContents(sockAddr, packetData, packetLength); +NetworkPacket::NetworkPacket(const HifiSockAddr& sockAddr, const QByteArray& packet) { + copyContents(sockAddr, packet); }; // copy assignment NetworkPacket& NetworkPacket::operator=(NetworkPacket const& other) { - copyContents(other.getSockAddr(), other.getData(), other.getLength()); + copyContents(other.getSockAddr(), other.getByteArray()); return *this; } #ifdef HAS_MOVE_SEMANTICS // move, same as copy, but other packet won't be used further NetworkPacket::NetworkPacket(NetworkPacket && packet) { - copyContents(packet.getAddress(), packet.getData(), packet.getLength()); + copyContents(packet.getAddress(), packet.getByteArray()); } // move assignment NetworkPacket& NetworkPacket::operator=(NetworkPacket&& other) { - _packetLength = 0; - copyContents(other.getAddress(), other.getData(), other.getLength()); + copyContents(other.getAddress(), other.getByteArray()); return *this; } #endif \ No newline at end of file diff --git a/libraries/shared/src/NetworkPacket.h b/libraries/shared/src/NetworkPacket.h index 7eef1e7129..480a793a49 100644 --- a/libraries/shared/src/NetworkPacket.h +++ b/libraries/shared/src/NetworkPacket.h @@ -25,9 +25,7 @@ /// Storage of not-yet processed inbound, or not yet sent outbound generic UDP network packet class NetworkPacket { public: - NetworkPacket(); NetworkPacket(const NetworkPacket& packet); // copy constructor - ~NetworkPacket(); // destructor NetworkPacket& operator= (const NetworkPacket& other); // copy assignment #ifdef HAS_MOVE_SEMANTICS @@ -35,21 +33,16 @@ public: NetworkPacket& operator= (NetworkPacket&& other); // move assignment #endif - NetworkPacket(const HifiSockAddr& sockAddr, unsigned char* packetData, ssize_t packetLength); + NetworkPacket(const HifiSockAddr& sockAddr, const QByteArray& byteArray); const HifiSockAddr& getSockAddr() const { return _sockAddr; } - ssize_t getLength() const { return _packetLength; } - unsigned char* getData() { return &_packetData[0]; } - - const HifiSockAddr& getAddress() const { return _sockAddr; } - const unsigned char* getData() const { return &_packetData[0]; } + const QByteArray& getByteArray() const { return _byteArray; } private: - void copyContents(const HifiSockAddr& sockAddr, const unsigned char* packetData, ssize_t packetLength); + void copyContents(const HifiSockAddr& sockAddr, const QByteArray& byteArray); HifiSockAddr _sockAddr; - ssize_t _packetLength; - unsigned char _packetData[MAX_PACKET_SIZE]; + QByteArray _byteArray; }; #endif /* defined(__shared_NetworkPacket__) */ diff --git a/libraries/shared/src/Node.cpp b/libraries/shared/src/Node.cpp index 603e1febba..37628fb649 100644 --- a/libraries/shared/src/Node.cpp +++ b/libraries/shared/src/Node.cpp @@ -16,7 +16,6 @@ #endif #include "Node.h" -#include "NodeTypes.h" #include "SharedUtil.h" #include @@ -135,6 +134,24 @@ float Node::getAverageKilobitsPerSecond() { } } +QDataStream& operator>>(QDataStream& out, const Node& node) { + out << node._type; + out << node._uuid; + out << node._publicSocket; + out << node._localSocket; + + return out; +} + +QDataStream& operator<<(QDataStream& in, Node& node) { + in >> node._type; + in >> node._uuid; + in >> node._publicSocket; + in >> node._localSocket; + + return in; +} + QDebug operator<<(QDebug debug, const Node &node) { debug.nospace() << node.getTypeName() << " (" << node.getType() << ")"; debug << " " << node.getUUID().toString().toLocal8Bit().constData() << " "; diff --git a/libraries/shared/src/Node.h b/libraries/shared/src/Node.h index 352498cd61..eacbc93892 100644 --- a/libraries/shared/src/Node.h +++ b/libraries/shared/src/Node.h @@ -27,6 +27,18 @@ #include "NodeData.h" #include "SimpleMovingAverage.h" +typedef quint8 NODE_TYPE; +const NODE_TYPE NODE_TYPE_DOMAIN = 'D'; +const NODE_TYPE NODE_TYPE_VOXEL_SERVER = 'V'; +const NODE_TYPE NODE_TYPE_PARTICLE_SERVER = 'P'; +const NODE_TYPE NODE_TYPE_METAVOXEL_SERVER = 'm'; +const NODE_TYPE NODE_TYPE_ENVIRONMENT_SERVER = 'E'; +const NODE_TYPE NODE_TYPE_AGENT = 'I'; +const NODE_TYPE NODE_TYPE_AUDIO_MIXER = 'M'; +const NODE_TYPE NODE_TYPE_AVATAR_MIXER = 'W'; +const NODE_TYPE NODE_TYPE_ANIMATION_SERVER = 'a'; +const NODE_TYPE NODE_TYPE_UNASSIGNED = 1; + class Node : public QObject { Q_OBJECT public: @@ -75,13 +87,16 @@ public: int getClockSkewUsec() const { return _clockSkewUsec; } void setClockSkewUsec(int clockSkew) { _clockSkewUsec = clockSkew; } QMutex& getMutex() { return _mutex; } + + friend QDataStream& operator>>(QDataStream& out, const Node& node); + friend QDataStream& operator<<(QDataStream& in, Node& node); private: // privatize copy and assignment operator to disallow Node copying Node(const Node &otherNode); Node& operator=(Node otherNode); - char _type; + NODE_TYPE _type; QUuid _uuid; uint64_t _wakeMicrostamp; uint64_t _lastHeardMicrostamp; diff --git a/libraries/shared/src/NodeData.h b/libraries/shared/src/NodeData.h index af5d13cd04..cf800fc3cd 100644 --- a/libraries/shared/src/NodeData.h +++ b/libraries/shared/src/NodeData.h @@ -18,7 +18,7 @@ class NodeData : public QObject { public: virtual ~NodeData() = 0; - virtual int parseData(unsigned char* sourceBuffer, int numBytes) = 0; + virtual int parseData(const QByteArray& packet) = 0; }; #endif diff --git a/libraries/shared/src/NodeList.cpp b/libraries/shared/src/NodeList.cpp index 5c5791d475..4d43159f52 100644 --- a/libraries/shared/src/NodeList.cpp +++ b/libraries/shared/src/NodeList.cpp @@ -17,7 +17,6 @@ #include "HifiSockAddr.h" #include "Logging.h" #include "NodeList.h" -#include "NodeTypes.h" #include "PacketHeaders.h" #include "SharedUtil.h" #include "UUID.h" @@ -109,79 +108,83 @@ void NodeList::setDomainHostname(const QString& domainHostname) { } } -void NodeList::timePingReply(const HifiSockAddr& nodeAddress, unsigned char *packetData) { - foreach (const SharedNodePointer& node, _nodeHash) { - if (node->getPublicSocket() == nodeAddress || - node->getLocalSocket() == nodeAddress) { - - unsigned char* dataAt = packetData + numBytesForPacketHeader(packetData); - uint64_t ourOriginalTime = *(uint64_t*)(dataAt); - dataAt += sizeof(ourOriginalTime); - uint64_t othersReplyTime = *(uint64_t*)(dataAt); - uint64_t now = usecTimestampNow(); - int pingTime = now - ourOriginalTime; - int oneWayFlightTime = pingTime / 2; // half of the ping is our one way flight - - // The other node's expected time should be our original time plus the one way flight time - // anything other than that is clock skew - uint64_t othersExprectedReply = ourOriginalTime + oneWayFlightTime; - int clockSkew = othersReplyTime - othersExprectedReply; - - node->setPingMs(pingTime / 1000); - node->setClockSkewUsec(clockSkew); - - const bool wantDebug = false; - if (wantDebug) { - qDebug() << "PING_REPLY from node " << *node << "\n" << - " now: " << now << "\n" << - " ourTime: " << ourOriginalTime << "\n" << - " pingTime: " << pingTime << "\n" << - " oneWayFlightTime: " << oneWayFlightTime << "\n" << - " othersReplyTime: " << othersReplyTime << "\n" << - " othersExprectedReply: " << othersExprectedReply << "\n" << - " clockSkew: " << clockSkew; - } - break; +void NodeList::timePingReply(const QByteArray& packet) { + QUuid nodeUUID; + deconstructPacketHeader(packet, nodeUUID); + + SharedNodePointer matchingNode = nodeWithUUID(nodeUUID); + + if (matchingNode) { + QDataStream packetStream(packet); + packetStream.device()->seek(numBytesForPacketHeader(packet)); + + qint64 ourOriginalTime, othersReplyTime; + + packetStream >> ourOriginalTime >> othersReplyTime; + + qint64 now = usecTimestampNow(); + int pingTime = now - ourOriginalTime; + int oneWayFlightTime = pingTime / 2; // half of the ping is our one way flight + + // The other node's expected time should be our original time plus the one way flight time + // anything other than that is clock skew + uint64_t othersExprectedReply = ourOriginalTime + oneWayFlightTime; + int clockSkew = othersReplyTime - othersExprectedReply; + + matchingNode->setPingMs(pingTime / 1000); + matchingNode->setClockSkewUsec(clockSkew); + + const bool wantDebug = false; + + if (wantDebug) { + qDebug() << "PING_REPLY from node " << *matchingNode << "\n" << + " now: " << now << "\n" << + " ourTime: " << ourOriginalTime << "\n" << + " pingTime: " << pingTime << "\n" << + " oneWayFlightTime: " << oneWayFlightTime << "\n" << + " othersReplyTime: " << othersReplyTime << "\n" << + " othersExprectedReply: " << othersExprectedReply << "\n" << + " clockSkew: " << clockSkew; } } } -void NodeList::processNodeData(const HifiSockAddr& senderSockAddr, unsigned char* packetData, size_t dataBytes) { - switch (packetData[0]) { - case PACKET_TYPE_DOMAIN: { +void NodeList::processNodeData(const HifiSockAddr& senderSockAddr, const QByteArray& packet) { + switch (packetTypeForPacket(packet)) { + case PacketTypeDomainList: { // only process the DS if this is our current domain server if (_domainSockAddr == senderSockAddr) { - processDomainServerList(packetData, dataBytes); + processDomainServerList(packet); } break; } - case PACKET_TYPE_PING: { + case PacketTypePing: { // send back a reply - unsigned char replyPacket[MAX_PACKET_SIZE]; - int replyPacketLength = fillPingReplyPacket(packetData, replyPacket); - _nodeSocket.writeDatagram((char*)replyPacket, replyPacketLength, - senderSockAddr.getAddress(), senderSockAddr.getPort()); + QByteArray replyPacket = constructPingReplyPacket(packet); + _nodeSocket.writeDatagram(replyPacket, senderSockAddr.getAddress(), senderSockAddr.getPort()); break; } - case PACKET_TYPE_PING_REPLY: { + case PacketTypePingReply: { // activate the appropriate socket for this node, if not yet updated activateSocketFromNodeCommunication(senderSockAddr); // set the ping time for this node for stat collection - timePingReply(senderSockAddr, packetData); + timePingReply(packet); break; } - case PACKET_TYPE_STUN_RESPONSE: { + case PacketTypeStunResponse: { // a STUN packet begins with 00, we've checked the second zero with packetVersionMatch // pass it along so it can be processed into our public address and port - processSTUNResponse(packetData, dataBytes); + processSTUNResponse(packet); break; } + default: + break; } } -int NodeList::updateNodeWithData(Node *node, const HifiSockAddr& senderSockAddr, unsigned char *packetData, int dataBytes) { +int NodeList::updateNodeWithData(Node *node, const HifiSockAddr& senderSockAddr, const QByteArray& packet) { QMutexLocker locker(&node->getMutex()); node->setLastHeardMicrostamp(usecTimestampNow()); @@ -195,13 +198,13 @@ int NodeList::updateNodeWithData(Node *node, const HifiSockAddr& senderSockAddr, } if (node->getActiveSocket() || senderSockAddr.isNull()) { - node->recordBytesReceived(dataBytes); + node->recordBytesReceived(packet.size()); if (!node->getLinkedData() && linkedDataCreateCallback) { linkedDataCreateCallback(node); } - int numParsedBytes = node->getLinkedData()->parseData(packetData, dataBytes); + int numParsedBytes = node->getLinkedData()->parseData(packet); return numParsedBytes; } else { // we weren't able to match the sender address to the address we have for this node, unlock and don't parse @@ -323,7 +326,7 @@ void NodeList::sendSTUNRequest() { } } -void NodeList::processSTUNResponse(unsigned char* packetData, size_t dataBytes) { +void NodeList::processSTUNResponse(const QByteArray& packet) { // check the cookie to make sure this is actually a STUN response // and read the first attribute and make sure it is a XOR_MAPPED_ADDRESS const int NUM_BYTES_MESSAGE_TYPE_AND_LENGTH = 4; @@ -333,13 +336,13 @@ void NodeList::processSTUNResponse(unsigned char* packetData, size_t dataBytes) size_t attributeStartIndex = NUM_BYTES_STUN_HEADER; - if (memcmp(packetData + NUM_BYTES_MESSAGE_TYPE_AND_LENGTH, + if (memcmp(packet.data() + NUM_BYTES_MESSAGE_TYPE_AND_LENGTH, &RFC_5389_MAGIC_COOKIE_NETWORK_ORDER, sizeof(RFC_5389_MAGIC_COOKIE_NETWORK_ORDER)) == 0) { // enumerate the attributes to find XOR_MAPPED_ADDRESS_TYPE - while (attributeStartIndex < dataBytes) { - if (memcmp(packetData + attributeStartIndex, &XOR_MAPPED_ADDRESS_TYPE, sizeof(XOR_MAPPED_ADDRESS_TYPE)) == 0) { + while (attributeStartIndex < packet.size()) { + if (memcmp(packet.data() + attributeStartIndex, &XOR_MAPPED_ADDRESS_TYPE, sizeof(XOR_MAPPED_ADDRESS_TYPE)) == 0) { const int NUM_BYTES_STUN_ATTR_TYPE_AND_LENGTH = 4; const int NUM_BYTES_FAMILY_ALIGN = 1; const uint8_t IPV4_FAMILY_NETWORK_ORDER = htons(0x01) >> 8; @@ -347,17 +350,17 @@ void NodeList::processSTUNResponse(unsigned char* packetData, size_t dataBytes) // reset the number of failed STUN requests since last success _stunRequestsSinceSuccess = 0; - int byteIndex = attributeStartIndex + NUM_BYTES_STUN_ATTR_TYPE_AND_LENGTH + NUM_BYTES_FAMILY_ALIGN; - + int byteIndex = attributeStartIndex + NUM_BYTES_STUN_ATTR_TYPE_AND_LENGTH + NUM_BYTES_FAMILY_ALIGN; + uint8_t addressFamily = 0; - memcpy(&addressFamily, packetData + byteIndex, sizeof(addressFamily)); + memcpy(&addressFamily, packet.data(), sizeof(addressFamily)); byteIndex += sizeof(addressFamily); if (addressFamily == IPV4_FAMILY_NETWORK_ORDER) { // grab the X-Port uint16_t xorMappedPort = 0; - memcpy(&xorMappedPort, packetData + byteIndex, sizeof(xorMappedPort)); + memcpy(&xorMappedPort, packet.data() + byteIndex, sizeof(xorMappedPort)); uint16_t newPublicPort = ntohs(xorMappedPort) ^ (ntohl(RFC_5389_MAGIC_COOKIE_NETWORK_ORDER) >> 16); @@ -365,7 +368,7 @@ void NodeList::processSTUNResponse(unsigned char* packetData, size_t dataBytes) // grab the X-Address uint32_t xorMappedAddress = 0; - memcpy(&xorMappedAddress, packetData + byteIndex, sizeof(xorMappedAddress)); + memcpy(&xorMappedAddress, packet.data() + byteIndex, sizeof(xorMappedAddress)); uint32_t stunAddress = ntohl(xorMappedAddress) ^ ntohl(RFC_5389_MAGIC_COOKIE_NETWORK_ORDER); @@ -389,7 +392,8 @@ void NodeList::processSTUNResponse(unsigned char* packetData, size_t dataBytes) const int NUM_BYTES_ATTRIBUTE_TYPE = 2; uint16_t attributeLength = 0; - memcpy(&attributeLength, packetData + attributeStartIndex + NUM_BYTES_ATTRIBUTE_TYPE, sizeof(attributeLength)); + memcpy(&attributeLength, packet.data() + attributeStartIndex + NUM_BYTES_ATTRIBUTE_TYPE, + sizeof(attributeLength)); attributeLength = ntohs(attributeLength); attributeStartIndex += NUM_BYTES_MESSAGE_TYPE_AND_LENGTH + attributeLength; @@ -415,11 +419,8 @@ NodeHash::iterator NodeList::killNodeAtHashIterator(NodeHash::iterator& nodeItem void NodeList::processKillNode(const QByteArray& dataByteArray) { // read the node id - QUuid nodeUUID = QUuid::fromRfc4122(dataByteArray.mid(numBytesForPacketHeader(reinterpret_cast - (dataByteArray.data())), - NUM_BYTES_RFC4122_UUID)); + QUuid nodeUUID = QUuid::fromRfc4122(dataByteArray.mid(numBytesForPacketHeader(dataByteArray), NUM_BYTES_RFC4122_UUID)); - // kill the node with this UUID, if it exists killNodeWithUUID(nodeUUID); } @@ -459,53 +460,22 @@ void NodeList::sendDomainServerCheckIn() { sendSTUNRequest(); } else { // construct the DS check in packet if we need to - int numBytesNodesOfInterest = _nodeTypesOfInterest.size(); - - const int IP_ADDRESS_BYTES = 4; // check in packet has header, optional UUID, node type, port, IP, node types of interest, null termination - #ifdef _WIN32 - const int numPacketBytes = MAX_PACKET_SIZE; - #else - int numPacketBytes = sizeof(PACKET_TYPE) + sizeof(PACKET_VERSION) + sizeof(NODE_TYPE) + - NUM_BYTES_RFC4122_UUID + (2 * (sizeof(uint16_t) + IP_ADDRESS_BYTES)) + - numBytesNodesOfInterest + sizeof(unsigned char); - #endif - - unsigned char checkInPacket[numPacketBytes]; - unsigned char* packetPosition = checkInPacket; - - PACKET_TYPE nodePacketType = (memchr(SOLO_NODE_TYPES, _ownerType, sizeof(SOLO_NODE_TYPES))) - ? PACKET_TYPE_DOMAIN_REPORT_FOR_DUTY - : PACKET_TYPE_DOMAIN_LIST_REQUEST; - - packetPosition += populateTypeAndVersion(packetPosition, nodePacketType); - - *(packetPosition++) = _ownerType; - - // send our owner UUID or the null one - QByteArray rfcOwnerUUID = _ownerUUID.toRfc4122(); - memcpy(packetPosition, rfcOwnerUUID.constData(), rfcOwnerUUID.size()); - packetPosition += rfcOwnerUUID.size(); - - // pack our public address to send to domain-server - packetPosition += HifiSockAddr::packSockAddr(checkInPacket + (packetPosition - checkInPacket), _publicSockAddr); - - // pack our local address to send to domain-server - packetPosition += HifiSockAddr::packSockAddr(checkInPacket + (packetPosition - checkInPacket), - HifiSockAddr(QHostAddress(getHostOrderLocalAddress()), - _nodeSocket.localPort())); - - // add the number of bytes for node types of interest - *(packetPosition++) = numBytesNodesOfInterest; - + QByteArray domainServerPacket = byteArrayWithPopluatedHeader(PacketTypeDomainListRequest); + QDataStream packetStream(&domainServerPacket, QIODevice::Append); + + // pack our data to send to the domain-server + packetStream << _ownerType << _publicSockAddr + << HifiSockAddr(QHostAddress(getHostOrderLocalAddress()), _nodeSocket.localPort()) + << (char) _nodeTypesOfInterest.size(); + // copy over the bytes for node types of interest, if required foreach (NODE_TYPE nodeTypeOfInterest, _nodeTypesOfInterest) { - *(packetPosition++) = nodeTypeOfInterest; + packetStream << nodeTypeOfInterest; } - _nodeSocket.writeDatagram((char*) checkInPacket, packetPosition - checkInPacket, - _domainSockAddr.getAddress(), _domainSockAddr.getPort()); + _nodeSocket.writeDatagram(domainServerPacket, _domainSockAddr.getAddress(), _domainSockAddr.getPort()); const int NUM_DOMAIN_SERVER_CHECKINS_PER_STUN_REQUEST = 5; static unsigned int numDomainCheckins = 0; @@ -519,28 +489,25 @@ void NodeList::sendDomainServerCheckIn() { } } -int NodeList::processDomainServerList(unsigned char* packetData, size_t dataBytes) { +int NodeList::processDomainServerList(const QByteArray& packet) { // this is a packet from the domain server, reset the count of un-replied check-ins _numNoReplyDomainCheckIns = 0; int readNodes = 0; + + // setup variables to read into from QDataStream + qint8 nodeType; + + QUuid nodeUUID; - char nodeType; - - // assumes only IPv4 addresses HifiSockAddr nodePublicSocket; HifiSockAddr nodeLocalSocket; + + QDataStream packetStream(packet); + packetStream.skipRawData(numBytesForPacketHeader(packet)); - unsigned char* readPtr = packetData + numBytesForPacketHeader(packetData); - unsigned char* startPtr = packetData; - - while((size_t)(readPtr - startPtr) < dataBytes - sizeof(uint16_t)) { - nodeType = *readPtr++; - QUuid nodeUUID = QUuid::fromRfc4122(QByteArray((char*) readPtr, NUM_BYTES_RFC4122_UUID)); - readPtr += NUM_BYTES_RFC4122_UUID; - - readPtr += HifiSockAddr::unpackSockAddr(readPtr, nodePublicSocket); - readPtr += HifiSockAddr::unpackSockAddr(readPtr, nodeLocalSocket); + while(!packetStream.atEnd()) { + packetStream >> nodeType >> nodeUUID >> nodePublicSocket >> nodeLocalSocket; // if the public socket address is 0 then it's reachable at the same IP // as the domain server @@ -551,19 +518,19 @@ int NodeList::processDomainServerList(unsigned char* packetData, size_t dataByte addOrUpdateNode(nodeUUID, nodeType, nodePublicSocket, nodeLocalSocket); } - return readNodes; } void NodeList::sendAssignment(Assignment& assignment) { - unsigned char assignmentPacket[MAX_PACKET_SIZE]; - - PACKET_TYPE assignmentPacketType = assignment.getCommand() == Assignment::CreateCommand - ? PACKET_TYPE_CREATE_ASSIGNMENT - : PACKET_TYPE_REQUEST_ASSIGNMENT; - - int numHeaderBytes = populateTypeAndVersion(assignmentPacket, assignmentPacketType); - int numAssignmentBytes = assignment.packToBuffer(assignmentPacket + numHeaderBytes); + + PacketType assignmentPacketType = assignment.getCommand() == Assignment::CreateCommand + ? PacketTypeCreateAssignment + : PacketTypeRequestAssignment; + + QByteArray packet = byteArrayWithPopluatedHeader(assignmentPacketType); + QDataStream packetStream(&packet, QIODevice::Append); + + packetStream << assignment; static HifiSockAddr DEFAULT_ASSIGNMENT_SOCKET(DEFAULT_ASSIGNMENT_SERVER_HOSTNAME, DEFAULT_DOMAIN_SERVER_PORT); @@ -571,9 +538,7 @@ void NodeList::sendAssignment(Assignment& assignment) { ? &DEFAULT_ASSIGNMENT_SOCKET : &_assignmentServerSocket; - _nodeSocket.writeDatagram((char*) assignmentPacket, numHeaderBytes + numAssignmentBytes, - assignmentServerSocket->getAddress(), - assignmentServerSocket->getPort()); + _nodeSocket.writeDatagram(packet, assignmentServerSocket->getAddress(), assignmentServerSocket->getPort()); } int NodeList::packOwnerUUID(unsigned char* packetData) { @@ -582,43 +547,36 @@ int NodeList::packOwnerUUID(unsigned char* packetData) { return rfcUUID.size(); } -int NodeList::fillPingPacket(unsigned char* buffer) { - int numHeaderBytes = populateTypeAndVersion(buffer, PACKET_TYPE_PING); - uint64_t currentTime = usecTimestampNow(); - memcpy(buffer + numHeaderBytes, ¤tTime, sizeof(currentTime)); - return numHeaderBytes + sizeof(currentTime); +QByteArray NodeList::constructPingPacket() { + QByteArray pingPacket = byteArrayWithPopluatedHeader(PacketTypePing); + + QDataStream packetStream(&pingPacket, QIODevice::Append); + packetStream << usecTimestampNow(); + + return pingPacket; } -int NodeList::fillPingReplyPacket(unsigned char* pingBuffer, unsigned char* replyBuffer) { - int numHeaderBytesOriginal = numBytesForPacketHeader(pingBuffer); - uint64_t timeFromOriginalPing = *(uint64_t*)(pingBuffer + numHeaderBytesOriginal); - - int numHeaderBytesReply = populateTypeAndVersion(replyBuffer, PACKET_TYPE_PING_REPLY); - int length = numHeaderBytesReply; - uint64_t ourReplyTime = usecTimestampNow(); - - unsigned char* dataAt = replyBuffer + numHeaderBytesReply; - memcpy(dataAt, &timeFromOriginalPing, sizeof(timeFromOriginalPing)); - dataAt += sizeof(timeFromOriginalPing); - length += sizeof(timeFromOriginalPing); - - memcpy(dataAt, &ourReplyTime, sizeof(ourReplyTime)); - dataAt += sizeof(ourReplyTime); - length += sizeof(ourReplyTime); - - return length; +QByteArray NodeList::constructPingReplyPacket(const QByteArray& pingPacket) { + QByteArray replyPacket; + + uint64_t timeFromOriginalPing; + memcpy(&timeFromOriginalPing, pingPacket.data() + numBytesForPacketHeader(pingPacket), sizeof(timeFromOriginalPing)); + + QDataStream packetStream(replyPacket); + + packetStream.device()->seek(populatePacketHeader(replyPacket, PacketTypePingReply)); + + packetStream << timeFromOriginalPing << usecTimestampNow(); + + return replyPacket; } - void NodeList::pingPublicAndLocalSocketsForInactiveNode(Node* node) { - unsigned char pingPacket[MAX_PACKET_SIZE]; - int pingPacketLength = fillPingPacket(pingPacket); + QByteArray pingPacket = constructPingPacket(); // send the ping packet to the local and public sockets for this node - _nodeSocket.writeDatagram((char*) pingPacket, pingPacketLength, - node->getLocalSocket().getAddress(), node->getLocalSocket().getPort()); - _nodeSocket.writeDatagram((char*) pingPacket, pingPacketLength, - node->getPublicSocket().getAddress(), node->getPublicSocket().getPort()); + _nodeSocket.writeDatagram(pingPacket, node->getLocalSocket().getAddress(), node->getLocalSocket().getPort()); + _nodeSocket.writeDatagram(pingPacket, node->getPublicSocket().getAddress(), node->getPublicSocket().getPort()); } SharedNodePointer NodeList::addOrUpdateNode(const QUuid& uuid, char nodeType, @@ -669,7 +627,7 @@ SharedNodePointer NodeList::addOrUpdateNode(const QUuid& uuid, char nodeType, } } -unsigned NodeList::broadcastToNodes(unsigned char* broadcastData, size_t dataBytes, +unsigned NodeList::broadcastToNodes(const QByteArray& packet, const QSet& destinationNodeTypes) { unsigned n = 0; @@ -678,8 +636,7 @@ unsigned NodeList::broadcastToNodes(unsigned char* broadcastData, size_t dataByt if (destinationNodeTypes.contains(node->getType())) { if (getNodeActiveSocketOrPing(node.data())) { // we know which socket is good for this node, send there - _nodeSocket.writeDatagram((char*) broadcastData, dataBytes, - node->getActiveSocket()->getAddress(), node->getActiveSocket()->getPort()); + _nodeSocket.writeDatagram(packet, node->getActiveSocket()->getAddress(), node->getActiveSocket()->getPort()); ++n; } } diff --git a/libraries/shared/src/NodeList.h b/libraries/shared/src/NodeList.h index c660517add..b987cd0e65 100644 --- a/libraries/shared/src/NodeList.h +++ b/libraries/shared/src/NodeList.h @@ -29,7 +29,6 @@ #include #include "Node.h" -#include "NodeTypes.h" const int MAX_NUM_NODES = 10000; const int NODES_PER_BUCKET = 100; @@ -94,15 +93,15 @@ public: void addNodeTypeToInterestSet(NODE_TYPE nodeTypeToAdd); void addSetOfNodeTypesToNodeInterestSet(const QSet& setOfNodeTypes); - int processDomainServerList(unsigned char *packetData, size_t dataBytes); + int processDomainServerList(const QByteArray& packet); void setAssignmentServerSocket(const HifiSockAddr& serverSocket) { _assignmentServerSocket = serverSocket; } void sendAssignment(Assignment& assignment); int packOwnerUUID(unsigned char* packetData); - int fillPingPacket(unsigned char* buffer); - int fillPingReplyPacket(unsigned char* pingBuffer, unsigned char* replyBuffer); + QByteArray constructPingPacket(); + QByteArray constructPingReplyPacket(const QByteArray& pingPacket); void pingPublicAndLocalSocketsForInactiveNode(Node* node); SharedNodePointer nodeWithAddress(const HifiSockAddr& senderSockAddr); @@ -110,13 +109,12 @@ public: SharedNodePointer addOrUpdateNode(const QUuid& uuid, char nodeType, const HifiSockAddr& publicSocket, const HifiSockAddr& localSocket); - void processNodeData(const HifiSockAddr& senderSockAddr, unsigned char *packetData, size_t dataBytes); - + void processNodeData(const HifiSockAddr& senderSockAddr, const QByteArray& packet); void processKillNode(const QByteArray& datagram); - int updateNodeWithData(Node *node, const HifiSockAddr& senderSockAddr, unsigned char *packetData, int dataBytes); + int updateNodeWithData(Node *node, const HifiSockAddr& senderSockAddr, const QByteArray& packet); - unsigned broadcastToNodes(unsigned char *broadcastData, size_t dataBytes, const QSet& destinationNodeTypes); + unsigned broadcastToNodes(const QByteArray& packet, const QSet& destinationNodeTypes); SharedNodePointer soloNodeOfType(char nodeType); void loadData(QSettings* settings); @@ -141,7 +139,7 @@ private: NodeList(NodeList const&); // Don't implement, needed to avoid copies of singleton void operator=(NodeList const&); // Don't implement, needed to avoid copies of singleton void sendSTUNRequest(); - void processSTUNResponse(unsigned char* packetData, size_t dataBytes); + void processSTUNResponse(const QByteArray& packet); NodeHash::iterator killNodeAtHashIterator(NodeHash::iterator& nodeItemToKill); @@ -160,7 +158,7 @@ private: unsigned int _stunRequestsSinceSuccess; void activateSocketFromNodeCommunication(const HifiSockAddr& nodeSockAddr); - void timePingReply(const HifiSockAddr& nodeAddress, unsigned char *packetData); + void timePingReply(const QByteArray& packet); void resetDomainData(char domainField[], const char* domainData); void domainLookup(); void clear(); diff --git a/libraries/shared/src/NodeTypes.h b/libraries/shared/src/NodeTypes.h deleted file mode 100644 index 6e8523c7d7..0000000000 --- a/libraries/shared/src/NodeTypes.h +++ /dev/null @@ -1,31 +0,0 @@ -// -// NodeTypes.h -// hifi -// -// Created by Brad Hefta-Gaub on 2013/04/09 -// Copyright (c) 2013 HighFidelity, Inc. All rights reserved. -// -// Single byte/character Node Types used to identify various nodes in the system. -// For example, an node whose is 'V' is always a voxel server. - -#ifndef hifi_NodeTypes_h -#define hifi_NodeTypes_h - -// NOTE: If you add a new NODE_TYPE_XXX then you also should add a new NODE_TYPE_NAME_XXX and a new "case" to the -// switch statement in Node.cpp specifically Node::getTypeName(). -// If you don't then it will make things harder on your co-developers in debugging because the Node -// class won't know the name and will report it as "Unknown". - -typedef char NODE_TYPE; -const NODE_TYPE NODE_TYPE_DOMAIN = 'D'; -const NODE_TYPE NODE_TYPE_VOXEL_SERVER = 'V'; -const NODE_TYPE NODE_TYPE_PARTICLE_SERVER = 'P'; -const NODE_TYPE NODE_TYPE_METAVOXEL_SERVER = 'm'; -const NODE_TYPE NODE_TYPE_ENVIRONMENT_SERVER = 'E'; -const NODE_TYPE NODE_TYPE_AGENT = 'I'; -const NODE_TYPE NODE_TYPE_AUDIO_MIXER = 'M'; -const NODE_TYPE NODE_TYPE_AVATAR_MIXER = 'W'; -const NODE_TYPE NODE_TYPE_ANIMATION_SERVER = 'a'; -const NODE_TYPE NODE_TYPE_UNASSIGNED = 1; - -#endif diff --git a/libraries/shared/src/PacketHeaders.cpp b/libraries/shared/src/PacketHeaders.cpp index 24a34f618e..529f2639d7 100644 --- a/libraries/shared/src/PacketHeaders.cpp +++ b/libraries/shared/src/PacketHeaders.cpp @@ -6,105 +6,117 @@ // Copyright (c) 2013 HighFidelity, Inc. All rights reserved. // -#include +#include #include +#include "NodeList.h" +#include "UUID.h" + #include "PacketHeaders.h" -PACKET_VERSION versionForPacketType(PACKET_TYPE type) { +int arithmeticCodingValueFromBuffer(const char* checkValue) { + if (((int) *checkValue) < 255) { + return *checkValue; + } else { + return 255 + arithmeticCodingValueFromBuffer(checkValue + 1); + } +} + +int numBytesArithmeticCodingFromBuffer(const char* checkValue) { + if (((int) *checkValue) < 255) { + return *checkValue; + } else { + return 1 + numBytesArithmeticCodingFromBuffer(checkValue + 1); + } +} + +int packArithmeticallyCodedValue(int value, char* destination) { + if (value < 255) { + // less than 255, just pack our value + destination[0] = (char) value; + return 1; + } else { + // pack 255 and then recursively pack on + destination[0] = 255; + return 1 + packArithmeticallyCodedValue(value - 255, destination + 1); + } +} + +PacketVersion versionForPacketType(PacketType type) { switch (type) { - - case PACKET_TYPE_MICROPHONE_AUDIO_NO_ECHO: - case PACKET_TYPE_MICROPHONE_AUDIO_WITH_ECHO: - return 2; - - case PACKET_TYPE_HEAD_DATA: - return 17; - - case PACKET_TYPE_OCTREE_STATS: - return 2; - - case PACKET_TYPE_DOMAIN: - case PACKET_TYPE_DOMAIN_LIST_REQUEST: - case PACKET_TYPE_DOMAIN_REPORT_FOR_DUTY: - return 2; - - case PACKET_TYPE_VOXEL_QUERY: - return 2; - - case PACKET_TYPE_VOXEL_SET: - case PACKET_TYPE_VOXEL_SET_DESTRUCTIVE: - case PACKET_TYPE_VOXEL_ERASE: - return 1; - - case PACKET_TYPE_VOXEL_DATA: - return 1; - - case PACKET_TYPE_JURISDICTION: - return 1; - - case PACKET_TYPE_PARTICLE_ADD_OR_EDIT: - return 4; - - case PACKET_TYPE_PARTICLE_DATA: - return 8; - - case PACKET_TYPE_PING_REPLY: - return 1; - - case PACKET_TYPE_DATA_SERVER_GET: - case PACKET_TYPE_DATA_SERVER_PUT: - case PACKET_TYPE_DATA_SERVER_SEND: - case PACKET_TYPE_DATA_SERVER_CONFIRM: - return 1; - default: return 0; } } -bool packetVersionMatch(unsigned char* packetHeader, const HifiSockAddr& senderSockAddr) { +QByteArray byteArrayWithPopluatedHeader(PacketType type, const QUuid& connectionUUID) { + QByteArray freshByteArray; + populatePacketHeader(freshByteArray, type, connectionUUID); + return freshByteArray; +} + +int populatePacketHeader(QByteArray& packet, PacketType type, const QUuid& connectionUUID) { + return populatePacketHeader(packet.data(), type, connectionUUID); +} + +int populatePacketHeader(char* packet, PacketType type, const QUuid& connectionUUID) { + int numTypeBytes = packArithmeticallyCodedValue(type, packet); + packet[numTypeBytes] = versionForPacketType(type); + + QUuid packUUID = connectionUUID.isNull() ? NodeList::getInstance()->getOwnerUUID() : connectionUUID; + + QByteArray rfcUUID = packUUID.toRfc4122(); + memcpy(packet + numTypeBytes + sizeof(PacketVersion), rfcUUID, NUM_BYTES_RFC4122_UUID); + + // return the number of bytes written for pointer pushing + return numTypeBytes + sizeof(PacketVersion) + NUM_BYTES_RFC4122_UUID; + +} + +bool packetVersionMatch(const QByteArray& packet) { // currently this just checks if the version in the packet matches our return from versionForPacketType // may need to be expanded in the future for types and versions that take > than 1 byte - if (packetHeader[1] == versionForPacketType(packetHeader[0]) || packetHeader[0] == PACKET_TYPE_STUN_RESPONSE) { + + if (packet[1] == versionForPacketType(packetTypeForPacket(packet)) || packet[0] == PacketTypeStunResponse) { return true; } else { - qDebug() << "Packet mismatch on" << packetHeader[0] << "- Sender" - << senderSockAddr << "sent" << qPrintable(QString::number(packetHeader[1])) << "but" - << qPrintable(QString::number(versionForPacketType(packetHeader[0]))) << "expected."; + PacketType mismatchType = packetTypeForPacket(packet); + int numPacketTypeBytes = arithmeticCodingValueFromBuffer(packet.data()); + + QUuid nodeUUID; + deconstructPacketHeader(packet, nodeUUID); + + qDebug() << "Packet mismatch on" << packetTypeForPacket(packet) << "- Sender" + << nodeUUID << "sent" << qPrintable(QString::number(packet[numPacketTypeBytes])) << "but" + << qPrintable(QString::number(versionForPacketType(mismatchType))) << "expected."; + return false; } } -int populateTypeAndVersion(unsigned char* destinationHeader, PACKET_TYPE type) { - destinationHeader[0] = type; - destinationHeader[1] = versionForPacketType(type); - - // return the number of bytes written for pointer pushing - return 2; +int numBytesForPacketHeader(const QByteArray& packet) { + // returns the number of bytes used for the type, version, and UUID + return numBytesArithmeticCodingFromBuffer(packet.data()) + sizeof(PacketVersion) + NUM_BYTES_RFC4122_UUID; } -int numBytesForPacketType(const unsigned char* packetType) { - if (packetType[0] == 255) { - return 1 + numBytesForPacketType(packetType + 1); - } else { - return 1; - } +int numBytesForPacketHeader(const char* packet) { + // returns the number of bytes used for the type, version, and UUID + return numBytesArithmeticCodingFromBuffer(packet) + sizeof(PacketVersion) + NUM_BYTES_RFC4122_UUID; } -int numBytesForPacketVersion(const unsigned char* packetVersion) { - if (packetVersion[0] == 255) { - return 1 + numBytesForPacketVersion(packetVersion + 1); - } else { - return 1; - } +int numBytesForPacketHeaderGivenPacketType(PacketType type) { + return (int) ceilf((float)type) + sizeof(PacketVersion) + NUM_BYTES_RFC4122_UUID; } -int numBytesForPacketHeader(const unsigned char* packetHeader) { - // int numBytesType = numBytesForPacketType(packetHeader); - // return numBytesType + numBytesForPacketVersion(packetHeader + numBytesType); - - // currently this need not be dynamic - there are 2 bytes for each packet header - return 2; +void deconstructPacketHeader(const QByteArray& packet, QUuid& senderUUID) { + senderUUID = QUuid::fromRfc4122(packet.mid(arithmeticCodingValueFromBuffer(packet.data()) + sizeof(PacketVersion))); +} + +PacketType packetTypeForPacket(const QByteArray& packet) { + return (PacketType) arithmeticCodingValueFromBuffer(packet.data()); +} + +PacketType packetTypeForPacket(const char* packet) { + return (PacketType) arithmeticCodingValueFromBuffer(packet); } diff --git a/libraries/shared/src/PacketHeaders.h b/libraries/shared/src/PacketHeaders.h index 1febc9367d..e194406d58 100644 --- a/libraries/shared/src/PacketHeaders.h +++ b/libraries/shared/src/PacketHeaders.h @@ -12,61 +12,67 @@ #ifndef hifi_PacketHeaders_h #define hifi_PacketHeaders_h -#include "HifiSockAddr.h" +#include -typedef char PACKET_TYPE; -const PACKET_TYPE PACKET_TYPE_UNKNOWN = 0; -const PACKET_TYPE PACKET_TYPE_STUN_RESPONSE = 1; -const PACKET_TYPE PACKET_TYPE_DOMAIN = 'D'; -const PACKET_TYPE PACKET_TYPE_PING = 'P'; -const PACKET_TYPE PACKET_TYPE_PING_REPLY = 'R'; -const PACKET_TYPE PACKET_TYPE_KILL_AVATAR = 'K'; -const PACKET_TYPE PACKET_TYPE_HEAD_DATA = 'H'; -const PACKET_TYPE PACKET_TYPE_INJECT_AUDIO = 'I'; -const PACKET_TYPE PACKET_TYPE_MIXED_AUDIO = 'A'; -const PACKET_TYPE PACKET_TYPE_MICROPHONE_AUDIO_NO_ECHO = 'M'; -const PACKET_TYPE PACKET_TYPE_MICROPHONE_AUDIO_WITH_ECHO = 'm'; -const PACKET_TYPE PACKET_TYPE_BULK_AVATAR_DATA = 'X'; -const PACKET_TYPE PACKET_TYPE_TRANSMITTER_DATA_V2 = 'T'; -const PACKET_TYPE PACKET_TYPE_ENVIRONMENT_DATA = 'e'; -const PACKET_TYPE PACKET_TYPE_DOMAIN_LIST_REQUEST = 'L'; -const PACKET_TYPE PACKET_TYPE_DOMAIN_REPORT_FOR_DUTY = 'C'; -const PACKET_TYPE PACKET_TYPE_REQUEST_ASSIGNMENT = 'r'; -const PACKET_TYPE PACKET_TYPE_CREATE_ASSIGNMENT = 's'; -const PACKET_TYPE PACKET_TYPE_DEPLOY_ASSIGNMENT = 'd'; -const PACKET_TYPE PACKET_TYPE_DATA_SERVER_PUT = 'p'; -const PACKET_TYPE PACKET_TYPE_DATA_SERVER_GET = 'g'; -const PACKET_TYPE PACKET_TYPE_DATA_SERVER_SEND = 'u'; -const PACKET_TYPE PACKET_TYPE_DATA_SERVER_CONFIRM = 'c'; -const PACKET_TYPE PACKET_TYPE_VOXEL_QUERY = 'q'; -const PACKET_TYPE PACKET_TYPE_VOXEL_DATA = 'V'; -const PACKET_TYPE PACKET_TYPE_VOXEL_SET = 'S'; -const PACKET_TYPE PACKET_TYPE_VOXEL_SET_DESTRUCTIVE = 'O'; -const PACKET_TYPE PACKET_TYPE_VOXEL_ERASE = 'E'; -const PACKET_TYPE PACKET_TYPE_OCTREE_STATS = '#'; -const PACKET_TYPE PACKET_TYPE_JURISDICTION = 'J'; -const PACKET_TYPE PACKET_TYPE_JURISDICTION_REQUEST = 'j'; -const PACKET_TYPE PACKET_TYPE_PARTICLE_QUERY = 'Q'; -const PACKET_TYPE PACKET_TYPE_PARTICLE_DATA = 'v'; -const PACKET_TYPE PACKET_TYPE_PARTICLE_ADD_OR_EDIT = 'a'; -const PACKET_TYPE PACKET_TYPE_PARTICLE_ERASE = 'x'; -const PACKET_TYPE PACKET_TYPE_PARTICLE_ADD_RESPONSE = 'b'; -const PACKET_TYPE PACKET_TYPE_METAVOXEL_DATA = 't'; +enum PacketType { + PacketTypeUnknown, + PacketTypeStunResponse, + PacketTypeDomainList, + PacketTypePing, + PacketTypePingReply, + PacketTypeKillAvatar, + PacketTypeAvatarData, + PacketTypeInjectAudio, + PacketTypeMixedAudio, + PacketTypeMicrophoneAudioNoEcho, + PacketTypeMicrophoneAudioWithEcho, + PacketTypeBulkAvatarData, + PacketTypeTransmitterData, + PacketTypeEnvironmentData, + PacketTypeDomainListRequest, + PacketTypeRequestAssignment, + PacketTypeCreateAssignment, + PacketTypeDataServerPut, + PacketTypeDataServerGet, + PacketTypeDataServerSend, + PacketTypeDataServerConfirm, + PacketTypeVoxelQuery, + PacketTypeVoxelData, + PacketTypeVoxelSet, + PacketTypeVoxelSetDestructive, + PacketTypeVoxelErase, + PacketTypeOctreeStats, + PacketTypeJurisdiction, + PacketTypeJurisdictionRequest, + PacketTypeParticleQuery, + PacketTypeParticleData, + PacketTypeParticleAddOrEdit, + PacketTypeParticleErase, + PacketTypeParticleAddResponse, + PacketTypeMetavoxelData +}; -typedef char PACKET_VERSION; +typedef char PacketVersion; -PACKET_VERSION versionForPacketType(PACKET_TYPE type); +PacketVersion versionForPacketType(PacketType type); -bool packetVersionMatch(unsigned char* packetHeader, const HifiSockAddr& senderSockAddr); +const QUuid nullUUID = QUuid(); -int populateTypeAndVersion(unsigned char* destinationHeader, PACKET_TYPE type); -int numBytesForPacketHeader(const unsigned char* packetHeader); +QByteArray byteArrayWithPopluatedHeader(PacketType type, const QUuid& connectionUUID = nullUUID); +int populatePacketHeader(QByteArray& packet, PacketType type, const QUuid& connectionUUID = nullUUID); +int populatePacketHeader(char* packet, PacketType type, const QUuid& connectionUUID = nullUUID); -const int MAX_PACKET_HEADER_BYTES = sizeof(PACKET_TYPE) + sizeof(PACKET_VERSION); +bool packetVersionMatch(const QByteArray& packet); -// These are supported Z-Command -#define ERASE_ALL_COMMAND "erase all" -#define ADD_SCENE_COMMAND "add scene" -#define TEST_COMMAND "a message" +int numBytesForPacketHeader(const QByteArray& packet); +int numBytesForPacketHeader(const char* packet); +int numBytesForPacketHeaderGivenPacketType(PacketType type); + +void deconstructPacketHeader(const QByteArray& packet, QUuid& senderUUID); + +PacketType packetTypeForPacket(const QByteArray& packet); +PacketType packetTypeForPacket(const char* packet); + +int arithmeticCodingValueFromBuffer(const char* checkValue); #endif diff --git a/libraries/shared/src/PacketSender.cpp b/libraries/shared/src/PacketSender.cpp index 52274d9e9c..0cc37f356e 100644 --- a/libraries/shared/src/PacketSender.cpp +++ b/libraries/shared/src/PacketSender.cpp @@ -47,13 +47,13 @@ PacketSender::~PacketSender() { } -void PacketSender::queuePacketForSending(const HifiSockAddr& address, unsigned char* packetData, ssize_t packetLength) { - NetworkPacket packet(address, packetData, packetLength); +void PacketSender::queuePacketForSending(const HifiSockAddr& address, const QByteArray& packet) { + NetworkPacket networkPacket(address, packet); lock(); - _packets.push_back(packet); + _packets.push_back(networkPacket); unlock(); _totalPacketsQueued++; - _totalBytesQueued += packetLength; + _totalBytesQueued += packet.size(); } void PacketSender::setPacketsPerSecond(int packetsPerSecond) { @@ -263,15 +263,15 @@ bool PacketSender::nonThreadedProcess() { unlock(); // send the packet through the NodeList... - NodeList::getInstance()->getNodeSocket().writeDatagram((char*) temporary.getData(), temporary.getLength(), + NodeList::getInstance()->getNodeSocket().writeDatagram(temporary.getByteArray(), temporary.getSockAddr().getAddress(), temporary.getSockAddr().getPort()); packetsSentThisCall++; _packetsOverCheckInterval++; _totalPacketsSent++; - _totalBytesSent += temporary.getLength(); + _totalBytesSent += temporary.getByteArray().size(); - emit packetSent(temporary.getLength()); + emit packetSent(temporary.getByteArray().size()); _lastSendTime = now; } diff --git a/libraries/shared/src/PacketSender.h b/libraries/shared/src/PacketSender.h index 4d87a62e5a..415e084141 100644 --- a/libraries/shared/src/PacketSender.h +++ b/libraries/shared/src/PacketSender.h @@ -37,7 +37,7 @@ public: /// \param packetData pointer to data /// \param ssize_t packetLength size of data /// \thread any thread, typically the application thread - void queuePacketForSending(const HifiSockAddr& address, unsigned char* packetData, ssize_t packetLength); + void queuePacketForSending(const HifiSockAddr& address, const QByteArray& packet); void setPacketsPerSecond(int packetsPerSecond); int getPacketsPerSecond() const { return _packetsPerSecond; } diff --git a/libraries/shared/src/ReceivedPacketProcessor.cpp b/libraries/shared/src/ReceivedPacketProcessor.cpp index d61db2b184..a34e41006e 100644 --- a/libraries/shared/src/ReceivedPacketProcessor.cpp +++ b/libraries/shared/src/ReceivedPacketProcessor.cpp @@ -16,16 +16,16 @@ ReceivedPacketProcessor::ReceivedPacketProcessor() { _dontSleep = false; } -void ReceivedPacketProcessor::queueReceivedPacket(const HifiSockAddr& address, unsigned char* packetData, ssize_t packetLength) { +void ReceivedPacketProcessor::queueReceivedPacket(const HifiSockAddr& address, const QByteArray& packet) { // Make sure our Node and NodeList knows we've heard from this node. SharedNodePointer node = NodeList::getInstance()->nodeWithAddress(address); if (node) { node->setLastHeardMicrostamp(usecTimestampNow()); } - NetworkPacket packet(address, packetData, packetLength); + NetworkPacket networkPacket(address, packet); lock(); - _packets.push_back(packet); + _packets.push_back(networkPacket); unlock(); } @@ -44,7 +44,7 @@ bool ReceivedPacketProcessor::process() { NetworkPacket temporary = packet; // make a copy of the packet in case the vector is resized on us _packets.erase(_packets.begin()); // remove the oldest packet unlock(); // let others add to the packets - processPacket(temporary.getSockAddr(), temporary.getData(), temporary.getLength()); // process our temporary copy + processPacket(temporary.getSockAddr(), temporary.getByteArray()); // process our temporary copy } return isStillRunning(); // keep running till they terminate us } diff --git a/libraries/shared/src/ReceivedPacketProcessor.h b/libraries/shared/src/ReceivedPacketProcessor.h index 567434a49e..dfb4ed55a9 100644 --- a/libraries/shared/src/ReceivedPacketProcessor.h +++ b/libraries/shared/src/ReceivedPacketProcessor.h @@ -24,7 +24,7 @@ public: /// \param packetData pointer to received data /// \param ssize_t packetLength size of received data /// \thread network receive thread - void queueReceivedPacket(const HifiSockAddr& senderSockAddr, unsigned char* packetData, ssize_t packetLength); + void queueReceivedPacket(const HifiSockAddr& senderSockAddr, const QByteArray& packet); /// Are there received packets waiting to be processed bool hasPacketsToProcess() const { return _packets.size() > 0; } @@ -38,7 +38,7 @@ protected: /// \param packetData pointer to received data /// \param ssize_t packetLength size of received data /// \thread "this" individual processing thread - virtual void processPacket(const HifiSockAddr& senderAddress, unsigned char* packetData, ssize_t packetLength) = 0; + virtual void processPacket(const HifiSockAddr& senderAddress, const QByteArray& packet) = 0; /// Implements generic processing behavior for this thread. virtual bool process(); diff --git a/libraries/shared/src/SharedUtil.cpp b/libraries/shared/src/SharedUtil.cpp index 9433fe1236..9430fcde20 100644 --- a/libraries/shared/src/SharedUtil.cpp +++ b/libraries/shared/src/SharedUtil.cpp @@ -231,105 +231,6 @@ void sharedMessageHandler(QtMsgType type, const QMessageLogContext& context, con fprintf(stdout, "%s", message.toLocal8Bit().constData()); } -////////////////////////////////////////////////////////////////////////////////////////// -// Function: createVoxelEditMessage() -// Description: creates an "insert" or "remove" voxel message for a voxel code -// corresponding to the closest voxel which encloses a cube with -// lower corners at x,y,z, having side of length S. -// The input values x,y,z range 0.0 <= v < 1.0 -// message should be either 'S' for SET or 'E' for ERASE -// -// IMPORTANT: The buffer is returned to you a buffer which you MUST delete when you are -// done with it. -// -// HACK ATTACK: Well, what if this is larger than the MTU? That's the caller's problem, we -// just truncate the message -// -// Complaints: Brad :) -#define GUESS_OF_VOXELCODE_SIZE 10 -#define MAXIMUM_EDIT_VOXEL_MESSAGE_SIZE 1500 -#define SIZE_OF_COLOR_DATA sizeof(rgbColor) -bool createVoxelEditMessage(unsigned char command, short int sequence, - int voxelCount, VoxelDetail* voxelDetails, unsigned char*& bufferOut, int& sizeOut) { - - bool success = true; // assume the best - int messageSize = MAXIMUM_EDIT_VOXEL_MESSAGE_SIZE; // just a guess for now - unsigned char* messageBuffer = new unsigned char[messageSize]; - - int numBytesPacketHeader = populateTypeAndVersion(messageBuffer, command); - unsigned short int* sequenceAt = (unsigned short int*) &messageBuffer[numBytesPacketHeader]; - *sequenceAt = sequence; - - // pack in timestamp - uint64_t now = usecTimestampNow(); - uint64_t* timeAt = (uint64_t*)&messageBuffer[numBytesPacketHeader + sizeof(sequence)]; - *timeAt = now; - - unsigned char* copyAt = &messageBuffer[numBytesPacketHeader + sizeof(sequence) + sizeof(now)]; - int actualMessageSize = numBytesPacketHeader + sizeof(sequence) + sizeof(now); - - for (int i = 0; i < voxelCount && success; i++) { - // get the coded voxel - unsigned char* voxelData = pointToVoxel(voxelDetails[i].x,voxelDetails[i].y,voxelDetails[i].z, - voxelDetails[i].s,voxelDetails[i].red,voxelDetails[i].green,voxelDetails[i].blue); - - int lengthOfVoxelData = bytesRequiredForCodeLength(*voxelData)+SIZE_OF_COLOR_DATA; - - // make sure we have room to copy this voxel - if (actualMessageSize + lengthOfVoxelData > MAXIMUM_EDIT_VOXEL_MESSAGE_SIZE) { - success = false; - } else { - // add it to our message - memcpy(copyAt, voxelData, lengthOfVoxelData); - copyAt += lengthOfVoxelData; - actualMessageSize += lengthOfVoxelData; - } - // cleanup - delete[] voxelData; - } - - if (success) { - // finally, copy the result to the output - bufferOut = new unsigned char[actualMessageSize]; - sizeOut = actualMessageSize; - memcpy(bufferOut, messageBuffer, actualMessageSize); - } - - delete[] messageBuffer; // clean up our temporary buffer - return success; -} - -/// encodes the voxel details portion of a voxel edit message -bool encodeVoxelEditMessageDetails(unsigned char command, int voxelCount, VoxelDetail* voxelDetails, - unsigned char* bufferOut, int sizeIn, int& sizeOut) { - - bool success = true; // assume the best - unsigned char* copyAt = bufferOut; - sizeOut = 0; - - for (int i = 0; i < voxelCount && success; i++) { - // get the coded voxel - unsigned char* voxelData = pointToVoxel(voxelDetails[i].x,voxelDetails[i].y,voxelDetails[i].z, - voxelDetails[i].s,voxelDetails[i].red,voxelDetails[i].green,voxelDetails[i].blue); - - int lengthOfVoxelData = bytesRequiredForCodeLength(*voxelData)+SIZE_OF_COLOR_DATA; - - // make sure we have room to copy this voxel - if (sizeOut + lengthOfVoxelData > sizeIn) { - success = false; - } else { - // add it to our message - memcpy(copyAt, voxelData, lengthOfVoxelData); - copyAt += lengthOfVoxelData; - sizeOut += lengthOfVoxelData; - } - // cleanup - delete[] voxelData; - } - - return success; -} - unsigned char* pointToOctalCode(float x, float y, float z, float s) { return pointToVoxel(x, y, z, s); @@ -572,7 +473,7 @@ int packFloatVec3ToSignedTwoByteFixed(unsigned char* destBuffer, const glm::vec3 return destBuffer - startPosition; } -int unpackFloatVec3FromSignedTwoByteFixed(unsigned char* sourceBuffer, glm::vec3& destination, int radix) { +int unpackFloatVec3FromSignedTwoByteFixed(const unsigned char* sourceBuffer, glm::vec3& destination, int radix) { const unsigned char* startPosition = sourceBuffer; sourceBuffer += unpackFloatScalarFromSignedTwoByteFixed((int16_t*) sourceBuffer, &(destination.x), radix); sourceBuffer += unpackFloatScalarFromSignedTwoByteFixed((int16_t*) sourceBuffer, &(destination.y), radix); @@ -590,7 +491,7 @@ int packFloatAngleToTwoByte(unsigned char* buffer, float angle) { return sizeof(uint16_t); } -int unpackFloatAngleFromTwoByte(uint16_t* byteAnglePointer, float* destinationPointer) { +int unpackFloatAngleFromTwoByte(const uint16_t* byteAnglePointer, float* destinationPointer) { *destinationPointer = (*byteAnglePointer / (float) std::numeric_limits::max()) * 360.0 - 180; return sizeof(uint16_t); } @@ -607,7 +508,7 @@ int packOrientationQuatToBytes(unsigned char* buffer, const glm::quat& quatInput return sizeof(quatParts); } -int unpackOrientationQuatFromBytes(unsigned char* buffer, glm::quat& quatOutput) { +int unpackOrientationQuatFromBytes(const unsigned char* buffer, glm::quat& quatOutput) { uint16_t quatParts[4]; memcpy(&quatParts, buffer, sizeof(quatParts)); @@ -637,7 +538,7 @@ int packFloatRatioToTwoByte(unsigned char* buffer, float ratio) { return sizeof(ratioHolder); } -int unpackFloatRatioFromTwoByte(unsigned char* buffer, float& ratio) { +int unpackFloatRatioFromTwoByte(const unsigned char* buffer, float& ratio) { int16_t ratioHolder; memcpy(&ratioHolder, buffer, sizeof(ratioHolder)); @@ -668,7 +569,7 @@ int packClipValueToTwoByte(unsigned char* buffer, float clipValue) { return sizeof(holder); } -int unpackClipValueFromTwoByte(unsigned char* buffer, float& clipValue) { +int unpackClipValueFromTwoByte(const unsigned char* buffer, float& clipValue) { int16_t holder; memcpy(&holder, buffer, sizeof(holder)); @@ -690,7 +591,7 @@ int packFloatToByte(unsigned char* buffer, float value, float scaleBy) { return sizeof(holder); } -int unpackFloatFromByte(unsigned char* buffer, float& value, float scaleBy) { +int unpackFloatFromByte(const unsigned char* buffer, float& value, float scaleBy) { unsigned char holder; memcpy(&holder, buffer, sizeof(holder)); value = ((float)holder / (float) 255) * scaleBy; diff --git a/libraries/shared/src/SharedUtil.h b/libraries/shared/src/SharedUtil.h index a77663bbda..6498962fad 100644 --- a/libraries/shared/src/SharedUtil.h +++ b/libraries/shared/src/SharedUtil.h @@ -27,6 +27,8 @@ #include #endif +#include "PacketHeaders.h" + const int BYTES_PER_COLOR = 3; const int BYTES_PER_FLAGS = 1; typedef unsigned char rgbColor[BYTES_PER_COLOR]; @@ -107,13 +109,6 @@ struct VoxelDetail { unsigned char* pointToVoxel(float x, float y, float z, float s, unsigned char r = 0, unsigned char g = 0, unsigned char b = 0); unsigned char* pointToOctalCode(float x, float y, float z, float s); -// Creates a full Voxel edit message, including command header, sequence, and details -bool createVoxelEditMessage(unsigned char command, short int sequence, - int voxelCount, VoxelDetail* voxelDetails, unsigned char*& bufferOut, int& sizeOut); - -/// encodes the voxel details portion of a voxel edit message -bool encodeVoxelEditMessageDetails(unsigned char command, int voxelCount, VoxelDetail* voxelDetails, - unsigned char* bufferOut, int sizeIn, int& sizeOut); #ifdef _WIN32 void usleep(int waitTime); @@ -147,33 +142,33 @@ bool isBetween(int64_t value, int64_t max, int64_t min); // Angles are known to be between 0 and 360deg, this allows us to encode in 16bits with great accuracy int packFloatAngleToTwoByte(unsigned char* buffer, float angle); -int unpackFloatAngleFromTwoByte(uint16_t* byteAnglePointer, float* destinationPointer); +int unpackFloatAngleFromTwoByte(const uint16_t* byteAnglePointer, float* destinationPointer); // Orientation Quats are known to have 4 normalized components be between -1.0 and 1.0 // this allows us to encode each component in 16bits with great accuracy int packOrientationQuatToBytes(unsigned char* buffer, const glm::quat& quatInput); -int unpackOrientationQuatFromBytes(unsigned char* buffer, glm::quat& quatOutput); +int unpackOrientationQuatFromBytes(const unsigned char* buffer, glm::quat& quatOutput); // Ratios need the be highly accurate when less than 10, but not very accurate above 10, and they // are never greater than 1000 to 1, this allows us to encode each component in 16bits int packFloatRatioToTwoByte(unsigned char* buffer, float ratio); -int unpackFloatRatioFromTwoByte(unsigned char* buffer, float& ratio); +int unpackFloatRatioFromTwoByte(const unsigned char* buffer, float& ratio); // Near/Far Clip values need the be highly accurate when less than 10, but only integer accuracy above 10 and // they are never greater than 16,000, this allows us to encode each component in 16bits int packClipValueToTwoByte(unsigned char* buffer, float clipValue); -int unpackClipValueFromTwoByte(unsigned char* buffer, float& clipValue); +int unpackClipValueFromTwoByte(const unsigned char* buffer, float& clipValue); // Positive floats that don't need to be very precise int packFloatToByte(unsigned char* buffer, float value, float scaleBy); -int unpackFloatFromByte(unsigned char* buffer, float& value, float scaleBy); +int unpackFloatFromByte(const unsigned char* buffer, float& value, float scaleBy); // Allows sending of fixed-point numbers: radix 1 makes 15.1 number, radix 8 makes 8.8 number, etc int packFloatScalarToSignedTwoByteFixed(unsigned char* buffer, float scalar, int radix); -int unpackFloatScalarFromSignedTwoByteFixed(int16_t* byteFixedPointer, float* destinationPointer, int radix); +int unpackFloatScalarFromSignedTwoByteFixed(const int16_t* byteFixedPointer, float* destinationPointer, int radix); // A convenience for sending vec3's as fixed-poimt floats int packFloatVec3ToSignedTwoByteFixed(unsigned char* destBuffer, const glm::vec3& srcVector, int radix); -int unpackFloatVec3FromSignedTwoByteFixed(unsigned char* sourceBuffer, glm::vec3& destination, int radix); +int unpackFloatVec3FromSignedTwoByteFixed(const unsigned char* sourceBuffer, glm::vec3& destination, int radix); #endif /* defined(__hifi__SharedUtil__) */ diff --git a/libraries/shared/src/ThreadedAssignment.cpp b/libraries/shared/src/ThreadedAssignment.cpp index 7c7e07863a..148f06ec85 100644 --- a/libraries/shared/src/ThreadedAssignment.cpp +++ b/libraries/shared/src/ThreadedAssignment.cpp @@ -12,8 +12,8 @@ #include "Logging.h" #include "ThreadedAssignment.h" -ThreadedAssignment::ThreadedAssignment(const unsigned char* dataBuffer, int numBytes) : - Assignment(dataBuffer, numBytes), +ThreadedAssignment::ThreadedAssignment(const QByteArray& packet) : + Assignment(packet), _isFinished(false) { diff --git a/libraries/shared/src/ThreadedAssignment.h b/libraries/shared/src/ThreadedAssignment.h index 301a81bcf3..1f59aa4623 100644 --- a/libraries/shared/src/ThreadedAssignment.h +++ b/libraries/shared/src/ThreadedAssignment.h @@ -14,7 +14,7 @@ class ThreadedAssignment : public Assignment { Q_OBJECT public: - ThreadedAssignment(const unsigned char* dataBuffer, int numBytes); + ThreadedAssignment(const QByteArray& packet); void setFinished(bool isFinished); public slots: diff --git a/libraries/voxel-server/src/VoxelNodeData.h b/libraries/voxel-server/src/VoxelNodeData.h index 9697b9cec3..54ef9da5b6 100644 --- a/libraries/voxel-server/src/VoxelNodeData.h +++ b/libraries/voxel-server/src/VoxelNodeData.h @@ -15,7 +15,7 @@ class VoxelNodeData : public OctreeQueryNode { public: VoxelNodeData() : OctreeQueryNode() { }; - virtual PACKET_TYPE getMyPacketType() const { return PACKET_TYPE_VOXEL_DATA; } + virtual PacketType getMyPacketType() const { return PacketTypeVoxelData; } }; #endif /* defined(__hifi__VoxelNodeData__) */ diff --git a/libraries/voxel-server/src/VoxelServer.cpp b/libraries/voxel-server/src/VoxelServer.cpp index 3a8c0d1364..481a6c436b 100644 --- a/libraries/voxel-server/src/VoxelServer.cpp +++ b/libraries/voxel-server/src/VoxelServer.cpp @@ -16,7 +16,7 @@ const char* VOXEL_SERVER_NAME = "Voxel"; const char* VOXEL_SERVER_LOGGING_TARGET_NAME = "voxel-server"; const char* LOCAL_VOXELS_PERSIST_FILE = "resources/voxels.svo"; -VoxelServer::VoxelServer(const unsigned char* dataBuffer, int numBytes) : OctreeServer(dataBuffer, numBytes) { +VoxelServer::VoxelServer(const QByteArray& packet) : OctreeServer(packet) { // nothing special to do here... } @@ -38,7 +38,7 @@ bool VoxelServer::hasSpecialPacketToSend(Node* node) { } int VoxelServer::sendSpecialPacket(Node* node) { - int numBytesPacketHeader = populateTypeAndVersion(_tempOutputBuffer, PACKET_TYPE_ENVIRONMENT_DATA); + int numBytesPacketHeader = populatePacketHeader(reinterpret_cast(_tempOutputBuffer), PacketTypeEnvironmentData); int envPacketLength = numBytesPacketHeader; int environmentsToSend = getSendMinimalEnvironment() ? 1 : getEnvironmentDataCount(); diff --git a/libraries/voxel-server/src/VoxelServer.h b/libraries/voxel-server/src/VoxelServer.h index 06cea132c0..9e4a1d23df 100644 --- a/libraries/voxel-server/src/VoxelServer.h +++ b/libraries/voxel-server/src/VoxelServer.h @@ -25,7 +25,7 @@ /// Handles assignments of type VoxelServer - sending voxels to various clients. class VoxelServer : public OctreeServer { public: - VoxelServer(const unsigned char* dataBuffer, int numBytes); + VoxelServer(const QByteArray& packet); ~VoxelServer(); bool wantSendEnvironments() const { return _sendEnvironments; } @@ -37,7 +37,7 @@ public: virtual OctreeQueryNode* createOctreeQueryNode(); virtual Octree* createTree(); virtual unsigned char getMyNodeType() const { return NODE_TYPE_VOXEL_SERVER; } - virtual PACKET_TYPE getMyQueryMessageType() const { return PACKET_TYPE_VOXEL_QUERY; } + virtual PacketType getMyQueryMessageType() const { return PacketTypeVoxelQuery; } virtual const char* getMyServerName() const { return VOXEL_SERVER_NAME; } virtual const char* getMyLoggingServerTargetName() const { return VOXEL_SERVER_LOGGING_TARGET_NAME; } virtual const char* getMyDefaultPersistFilename() const { return LOCAL_VOXELS_PERSIST_FILE; } diff --git a/libraries/voxels/src/EnvironmentData.cpp b/libraries/voxels/src/EnvironmentData.cpp index 935d4601e9..5cee88e127 100644 --- a/libraries/voxels/src/EnvironmentData.cpp +++ b/libraries/voxels/src/EnvironmentData.cpp @@ -61,8 +61,8 @@ int EnvironmentData::getBroadcastData(unsigned char* destinationBuffer) const { return destinationBuffer - bufferStart; } -int EnvironmentData::parseData(unsigned char* sourceBuffer, int numBytes) { - unsigned char* startPosition = sourceBuffer; +int EnvironmentData::parseData(const unsigned char* sourceBuffer, int numBytes) { + const unsigned char* startPosition = sourceBuffer; memcpy(&_id, sourceBuffer, sizeof(_id)); sourceBuffer += sizeof(_id); diff --git a/libraries/voxels/src/EnvironmentData.h b/libraries/voxels/src/EnvironmentData.h index b801caba96..90cc0763fe 100644 --- a/libraries/voxels/src/EnvironmentData.h +++ b/libraries/voxels/src/EnvironmentData.h @@ -43,7 +43,7 @@ public: float getSunBrightness() const { return _sunBrightness; } int getBroadcastData(unsigned char* destinationBuffer) const; - int parseData(unsigned char* sourceBuffer, int numBytes); + int parseData(const unsigned char* sourceBuffer, int numBytes); private: diff --git a/libraries/voxels/src/VoxelEditPacketSender.cpp b/libraries/voxels/src/VoxelEditPacketSender.cpp index af3ae63377..c0477b683b 100644 --- a/libraries/voxels/src/VoxelEditPacketSender.cpp +++ b/libraries/voxels/src/VoxelEditPacketSender.cpp @@ -14,8 +14,106 @@ #include #include "VoxelEditPacketSender.h" +////////////////////////////////////////////////////////////////////////////////////////// +// Function: createVoxelEditMessage() +// Description: creates an "insert" or "remove" voxel message for a voxel code +// corresponding to the closest voxel which encloses a cube with +// lower corners at x,y,z, having side of length S. +// The input values x,y,z range 0.0 <= v < 1.0 +// message should be either 'S' for SET or 'E' for ERASE +// +// IMPORTANT: The buffer is returned to you a buffer which you MUST delete when you are +// done with it. +// +// HACK ATTACK: Well, what if this is larger than the MTU? That's the caller's problem, we +// just truncate the message +// +// Complaints: Brad :) +#define GUESS_OF_VOXELCODE_SIZE 10 +#define MAXIMUM_EDIT_VOXEL_MESSAGE_SIZE 1500 +#define SIZE_OF_COLOR_DATA sizeof(rgbColor) +bool createVoxelEditMessage(PacketType command, short int sequence, + int voxelCount, VoxelDetail* voxelDetails, unsigned char*& bufferOut, int& sizeOut) { + + bool success = true; // assume the best + int messageSize = MAXIMUM_EDIT_VOXEL_MESSAGE_SIZE; // just a guess for now + unsigned char* messageBuffer = new unsigned char[messageSize]; + + int numBytesPacketHeader = populatePacketHeader(reinterpret_cast(messageBuffer), command); + unsigned short int* sequenceAt = (unsigned short int*) &messageBuffer[numBytesPacketHeader]; + *sequenceAt = sequence; + + // pack in timestamp + uint64_t now = usecTimestampNow(); + uint64_t* timeAt = (uint64_t*)&messageBuffer[numBytesPacketHeader + sizeof(sequence)]; + *timeAt = now; + + unsigned char* copyAt = &messageBuffer[numBytesPacketHeader + sizeof(sequence) + sizeof(now)]; + int actualMessageSize = numBytesPacketHeader + sizeof(sequence) + sizeof(now); + + for (int i = 0; i < voxelCount && success; i++) { + // get the coded voxel + unsigned char* voxelData = pointToVoxel(voxelDetails[i].x,voxelDetails[i].y,voxelDetails[i].z, + voxelDetails[i].s,voxelDetails[i].red,voxelDetails[i].green,voxelDetails[i].blue); + + int lengthOfVoxelData = bytesRequiredForCodeLength(*voxelData)+SIZE_OF_COLOR_DATA; + + // make sure we have room to copy this voxel + if (actualMessageSize + lengthOfVoxelData > MAXIMUM_EDIT_VOXEL_MESSAGE_SIZE) { + success = false; + } else { + // add it to our message + memcpy(copyAt, voxelData, lengthOfVoxelData); + copyAt += lengthOfVoxelData; + actualMessageSize += lengthOfVoxelData; + } + // cleanup + delete[] voxelData; + } + + if (success) { + // finally, copy the result to the output + bufferOut = new unsigned char[actualMessageSize]; + sizeOut = actualMessageSize; + memcpy(bufferOut, messageBuffer, actualMessageSize); + } + + delete[] messageBuffer; // clean up our temporary buffer + return success; +} -void VoxelEditPacketSender::sendVoxelEditMessage(PACKET_TYPE type, VoxelDetail& detail) { +/// encodes the voxel details portion of a voxel edit message +bool encodeVoxelEditMessageDetails(PacketType, int voxelCount, VoxelDetail* voxelDetails, + unsigned char* bufferOut, int sizeIn, int& sizeOut) { + + bool success = true; // assume the best + unsigned char* copyAt = bufferOut; + sizeOut = 0; + + for (int i = 0; i < voxelCount && success; i++) { + // get the coded voxel + unsigned char* voxelData = pointToVoxel(voxelDetails[i].x,voxelDetails[i].y,voxelDetails[i].z, + voxelDetails[i].s,voxelDetails[i].red,voxelDetails[i].green,voxelDetails[i].blue); + + int lengthOfVoxelData = bytesRequiredForCodeLength(*voxelData)+SIZE_OF_COLOR_DATA; + + // make sure we have room to copy this voxel + if (sizeOut + lengthOfVoxelData > sizeIn) { + success = false; + } else { + // add it to our message + memcpy(copyAt, voxelData, lengthOfVoxelData); + copyAt += lengthOfVoxelData; + sizeOut += lengthOfVoxelData; + } + // cleanup + delete[] voxelData; + } + + return success; +} + +void VoxelEditPacketSender::sendVoxelEditMessage(PacketType type, VoxelDetail& detail) { // allows app to disable sending if for example voxels have been disabled if (!_shouldSend) { return; // bail early @@ -39,7 +137,7 @@ void VoxelEditPacketSender::sendVoxelEditMessage(PACKET_TYPE type, VoxelDetail& } } -void VoxelEditPacketSender::queueVoxelEditMessages(PACKET_TYPE type, int numberOfDetails, VoxelDetail* details) { +void VoxelEditPacketSender::queueVoxelEditMessages(PacketType type, int numberOfDetails, VoxelDetail* details) { if (!_shouldSend) { return; // bail early } @@ -54,4 +152,3 @@ void VoxelEditPacketSender::queueVoxelEditMessages(PACKET_TYPE type, int numberO } } } - diff --git a/libraries/voxels/src/VoxelEditPacketSender.h b/libraries/voxels/src/VoxelEditPacketSender.h index ec9b74dff8..d99c176d92 100644 --- a/libraries/voxels/src/VoxelEditPacketSender.h +++ b/libraries/voxels/src/VoxelEditPacketSender.h @@ -18,19 +18,19 @@ class VoxelEditPacketSender : public OctreeEditPacketSender { Q_OBJECT public: /// Send voxel edit message immediately - void sendVoxelEditMessage(PACKET_TYPE type, VoxelDetail& detail); + void sendVoxelEditMessage(PacketType type, VoxelDetail& detail); /// Queues a single voxel edit message. Will potentially send a pending multi-command packet. Determines which voxel-server /// node or nodes the packet should be sent to. Can be called even before voxel servers are known, in which case up to /// MaxPendingMessages will be buffered and processed when voxel servers are known. - void queueVoxelEditMessage(PACKET_TYPE type, unsigned char* codeColorBuffer, ssize_t length) { + void queueVoxelEditMessage(PacketType type, unsigned char* codeColorBuffer, ssize_t length) { queueOctreeEditMessage(type, codeColorBuffer, length); } /// Queues an array of several voxel edit messages. Will potentially send a pending multi-command packet. Determines /// which voxel-server node or nodes the packet should be sent to. Can be called even before voxel servers are known, in /// which case up to MaxPendingMessages will be buffered and processed when voxel servers are known. - void queueVoxelEditMessages(PACKET_TYPE type, int numberOfDetails, VoxelDetail* details); + void queueVoxelEditMessages(PacketType type, int numberOfDetails, VoxelDetail* details); /// call this to inform the VoxelEditPacketSender of the voxel server jurisdictions. This is required for normal operation. /// The internal contents of the jurisdiction map may change throughout the lifetime of the VoxelEditPacketSender. This map diff --git a/libraries/voxels/src/VoxelPacketData.h b/libraries/voxels/src/VoxelPacketData.h index 200bd7d30c..5cdc314503 100644 --- a/libraries/voxels/src/VoxelPacketData.h +++ b/libraries/voxels/src/VoxelPacketData.h @@ -31,14 +31,16 @@ typedef uint16_t VOXEL_PACKET_SEQUENCE; typedef uint64_t VOXEL_PACKET_SENT_TIME; typedef uint16_t VOXEL_PACKET_INTERNAL_SECTION_SIZE; const int MAX_VOXEL_PACKET_SIZE = MAX_PACKET_SIZE; -const int VOXEL_PACKET_HEADER_SIZE = (sizeof(PACKET_TYPE) + sizeof(PACKET_VERSION) + sizeof(VOXEL_PACKET_FLAGS) + +// this is overly conservative - uses 8 bytes for PacketType which could be as compact as a single byte +const int VOXEL_PACKET_HEADER_SIZE = (sizeof(PacketType) + sizeof(PacketVersion) + sizeof(VOXEL_PACKET_FLAGS) + sizeof(VOXEL_PACKET_SEQUENCE) + sizeof(VOXEL_PACKET_SENT_TIME)); const int MAX_VOXEL_PACKET_DATA_SIZE = MAX_PACKET_SIZE - VOXEL_PACKET_HEADER_SIZE; const int MAX_VOXEL_UNCOMRESSED_PACKET_SIZE = MAX_VOXEL_PACKET_DATA_SIZE; -/// Handles packing of the data portion of PACKET_TYPE_VOXEL_DATA messages. +/// Handles packing of the data portion of PacketType_VOXEL_DATA messages. class VoxelPacketData : public OctreePacketData { public: VoxelPacketData(bool enableCompression = false, int maxFinalizedSize = MAX_OCTREE_PACKET_DATA_SIZE); diff --git a/libraries/voxels/src/VoxelTree.cpp b/libraries/voxels/src/VoxelTree.cpp index 1a1f810661..90fdbb8a05 100644 --- a/libraries/voxels/src/VoxelTree.cpp +++ b/libraries/voxels/src/VoxelTree.cpp @@ -224,7 +224,7 @@ void VoxelTree::nudgeLeaf(VoxelTreeElement* element, void* extraData) { glm::vec3 nudge = args->nudgeVec; // delete the old element - args->voxelEditSenderPtr->sendVoxelEditMessage(PACKET_TYPE_VOXEL_ERASE, voxelDetails); + args->voxelEditSenderPtr->sendVoxelEditMessage(PacketTypeVoxelErase, voxelDetails); // nudge the old element voxelDetails.x += nudge.x; @@ -232,7 +232,7 @@ void VoxelTree::nudgeLeaf(VoxelTreeElement* element, void* extraData) { voxelDetails.z += nudge.z; // create a new voxel in its stead - args->voxelEditSenderPtr->sendVoxelEditMessage(PACKET_TYPE_VOXEL_SET_DESTRUCTIVE, voxelDetails); + args->voxelEditSenderPtr->sendVoxelEditMessage(PacketTypeVoxelSetDestructive, voxelDetails); } // Recurses voxel element with an operation function @@ -508,32 +508,33 @@ void VoxelTree::readCodeColorBufferToTreeRecursion(VoxelTreeElement* node, ReadC } } -bool VoxelTree::handlesEditPacketType(PACKET_TYPE packetType) const { +bool VoxelTree::handlesEditPacketType(PacketType packetType) const { // we handle these types of "edit" packets switch (packetType) { - case PACKET_TYPE_VOXEL_SET: - case PACKET_TYPE_VOXEL_SET_DESTRUCTIVE: - case PACKET_TYPE_VOXEL_ERASE: + case PacketTypeVoxelSet: + case PacketTypeVoxelSetDestructive: + case PacketTypeVoxelErase: return true; + default: + return false; + } - return false; } -int VoxelTree::processEditPacketData(PACKET_TYPE packetType, unsigned char* packetData, int packetLength, - unsigned char* editData, int maxLength, Node* senderNode) { - - int processedBytes = 0; +int VoxelTree::processEditPacketData(PacketType packetType, const unsigned char* packetData, int packetLength, + const unsigned char* editData, int maxLength, Node* senderNode) { + // we handle these types of "edit" packets switch (packetType) { - case PACKET_TYPE_VOXEL_SET: - case PACKET_TYPE_VOXEL_SET_DESTRUCTIVE: { - bool destructive = (packetType == PACKET_TYPE_VOXEL_SET_DESTRUCTIVE); + case PacketTypeVoxelSet: + case PacketTypeVoxelSetDestructive: { + bool destructive = (packetType == PacketTypeVoxelSetDestructive); int octets = numberOfThreeBitSectionsInCode(editData, maxLength); if (octets == OVERFLOWED_OCTCODE_BUFFER) { printf("WARNING! Got voxel edit record that would overflow buffer in numberOfThreeBitSectionsInCode(), "); printf("bailing processing of packet!\n"); - return processedBytes; + return 0; } const int COLOR_SIZE_IN_BYTES = 3; @@ -543,7 +544,7 @@ int VoxelTree::processEditPacketData(PACKET_TYPE packetType, unsigned char* pack if (voxelDataSize > maxLength) { printf("WARNING! Got voxel edit record that would overflow buffer, bailing processing of packet!\n"); printf("bailing processing of packet!\n"); - return processedBytes; + return 0; } readCodeColorBufferToTree(editData, destructive); @@ -551,10 +552,11 @@ int VoxelTree::processEditPacketData(PACKET_TYPE packetType, unsigned char* pack return voxelDataSize; } break; - case PACKET_TYPE_VOXEL_ERASE: + case PacketTypeVoxelErase: processRemoveOctreeElementsBitstream((unsigned char*)packetData, packetLength); return maxLength; + default: + return 0; } - return processedBytes; } diff --git a/libraries/voxels/src/VoxelTree.h b/libraries/voxels/src/VoxelTree.h index c30bc82aa8..4f30293766 100644 --- a/libraries/voxels/src/VoxelTree.h +++ b/libraries/voxels/src/VoxelTree.h @@ -51,10 +51,10 @@ public: void readCodeColorBufferToTree(const unsigned char* codeColorBuffer, bool destructive = false); - virtual PACKET_TYPE expectedDataPacketType() const { return PACKET_TYPE_VOXEL_DATA; } - virtual bool handlesEditPacketType(PACKET_TYPE packetType) const; - virtual int processEditPacketData(PACKET_TYPE packetType, unsigned char* packetData, int packetLength, - unsigned char* editData, int maxLength, Node* senderNode); + virtual PacketType expectedDataPacketType() const { return PacketTypeVoxelData; } + virtual bool handlesEditPacketType(PacketType packetType) const; + virtual int processEditPacketData(PacketType packetType, const unsigned char* packetData, int packetLength, + const unsigned char* editData, int maxLength, Node* senderNode); void processSetVoxelsBitstream(const unsigned char* bitstream, int bufferSizeBytes); /** diff --git a/libraries/voxels/src/VoxelsScriptingInterface.cpp b/libraries/voxels/src/VoxelsScriptingInterface.cpp index 3f4e19f60a..d82912c44b 100644 --- a/libraries/voxels/src/VoxelsScriptingInterface.cpp +++ b/libraries/voxels/src/VoxelsScriptingInterface.cpp @@ -8,7 +8,7 @@ #include "VoxelsScriptingInterface.h" -void VoxelsScriptingInterface::queueVoxelAdd(PACKET_TYPE addPacketType, VoxelDetail& addVoxelDetails) { +void VoxelsScriptingInterface::queueVoxelAdd(PacketType addPacketType, VoxelDetail& addVoxelDetails) { getVoxelPacketSender()->queueVoxelEditMessages(addPacketType, 1, &addVoxelDetails); } @@ -19,7 +19,7 @@ void VoxelsScriptingInterface::setVoxelNonDestructive(float x, float y, float z, scale / (float)TREE_SCALE, red, green, blue}; // queue the packet - queueVoxelAdd(PACKET_TYPE_VOXEL_SET, addVoxelDetail); + queueVoxelAdd(PacketTypeVoxelSet, addVoxelDetail); } void VoxelsScriptingInterface::setVoxel(float x, float y, float z, float scale, @@ -29,7 +29,7 @@ void VoxelsScriptingInterface::setVoxel(float x, float y, float z, float scale, scale / (float)TREE_SCALE, red, green, blue}; // queue the destructive add - queueVoxelAdd(PACKET_TYPE_VOXEL_SET_DESTRUCTIVE, addVoxelDetail); + queueVoxelAdd(PacketTypeVoxelSetDestructive, addVoxelDetail); } void VoxelsScriptingInterface::eraseVoxel(float x, float y, float z, float scale) { @@ -38,6 +38,6 @@ void VoxelsScriptingInterface::eraseVoxel(float x, float y, float z, float scale VoxelDetail deleteVoxelDetail = {x / (float)TREE_SCALE, y / (float)TREE_SCALE, z / (float)TREE_SCALE, scale / (float)TREE_SCALE, 0, 0, 0}; - getVoxelPacketSender()->queueVoxelEditMessages(PACKET_TYPE_VOXEL_ERASE, 1, &deleteVoxelDetail); + getVoxelPacketSender()->queueVoxelEditMessages(PacketTypeVoxelErase, 1, &deleteVoxelDetail); } diff --git a/libraries/voxels/src/VoxelsScriptingInterface.h b/libraries/voxels/src/VoxelsScriptingInterface.h index 97bdfb2c59..bef3b9782e 100644 --- a/libraries/voxels/src/VoxelsScriptingInterface.h +++ b/libraries/voxels/src/VoxelsScriptingInterface.h @@ -54,7 +54,7 @@ public slots: void eraseVoxel(float x, float y, float z, float scale); private: - void queueVoxelAdd(PACKET_TYPE addPacketType, VoxelDetail& addVoxelDetails); + void queueVoxelAdd(PacketType addPacketType, VoxelDetail& addVoxelDetails); }; class VoxelDetailScriptObject : public QObject { From 3854f75abd32f719da4104849be1215cf6998b1c Mon Sep 17 00:00:00 2001 From: Stephen Birarda Date: Tue, 28 Jan 2014 10:41:40 -0800 Subject: [PATCH 02/16] cleanup some UUID packing --- libraries/audio/src/PositionalAudioRingBuffer.cpp | 4 ++-- libraries/shared/src/NodeList.cpp | 6 ------ libraries/shared/src/NodeList.h | 2 -- 3 files changed, 2 insertions(+), 10 deletions(-) diff --git a/libraries/audio/src/PositionalAudioRingBuffer.cpp b/libraries/audio/src/PositionalAudioRingBuffer.cpp index fa515a5bf7..5434966c00 100644 --- a/libraries/audio/src/PositionalAudioRingBuffer.cpp +++ b/libraries/audio/src/PositionalAudioRingBuffer.cpp @@ -38,8 +38,8 @@ PositionalAudioRingBuffer::~PositionalAudioRingBuffer() { int PositionalAudioRingBuffer::parseData(const QByteArray& packet) { QDataStream packetStream(packet); - // skip the source UUID - packetStream.skipRawData(NUM_BYTES_RFC4122_UUID); + // skip the packet header (includes the source UUID) + packetStream.skipRawData(numBytesForPacketHeader(packet)); packetStream.skipRawData(parsePositionalData(packet.mid(packetStream.device()->pos()))); packetStream.skipRawData(writeData(packet.data() + packetStream.device()->pos(), diff --git a/libraries/shared/src/NodeList.cpp b/libraries/shared/src/NodeList.cpp index 4d43159f52..83e8d9824c 100644 --- a/libraries/shared/src/NodeList.cpp +++ b/libraries/shared/src/NodeList.cpp @@ -541,12 +541,6 @@ void NodeList::sendAssignment(Assignment& assignment) { _nodeSocket.writeDatagram(packet, assignmentServerSocket->getAddress(), assignmentServerSocket->getPort()); } -int NodeList::packOwnerUUID(unsigned char* packetData) { - QByteArray rfcUUID = _ownerUUID.toRfc4122(); - memcpy(packetData, rfcUUID.constData(), rfcUUID.size()); - return rfcUUID.size(); -} - QByteArray NodeList::constructPingPacket() { QByteArray pingPacket = byteArrayWithPopluatedHeader(PacketTypePing); diff --git a/libraries/shared/src/NodeList.h b/libraries/shared/src/NodeList.h index b987cd0e65..3f811dbad4 100644 --- a/libraries/shared/src/NodeList.h +++ b/libraries/shared/src/NodeList.h @@ -97,8 +97,6 @@ public: void setAssignmentServerSocket(const HifiSockAddr& serverSocket) { _assignmentServerSocket = serverSocket; } void sendAssignment(Assignment& assignment); - - int packOwnerUUID(unsigned char* packetData); QByteArray constructPingPacket(); QByteArray constructPingReplyPacket(const QByteArray& pingPacket); From 85ebad979f08cdb2ccb8fdaa9a1bb3d0f3f3689e Mon Sep 17 00:00:00 2001 From: Stephen Birarda Date: Tue, 28 Jan 2014 11:15:38 -0800 Subject: [PATCH 03/16] repair assignment flow errors from packet changes --- assignment-client/src/AssignmentClient.cpp | 56 +++++++++++---------- assignment-client/src/AssignmentFactory.cpp | 8 +-- domain-server/src/DomainServer.cpp | 1 + libraries/shared/src/Assignment.cpp | 9 ++-- libraries/shared/src/PacketHeaders.cpp | 18 ++++--- 5 files changed, 54 insertions(+), 38 deletions(-) diff --git a/assignment-client/src/AssignmentClient.cpp b/assignment-client/src/AssignmentClient.cpp index 998ff46217..8725c6ca56 100644 --- a/assignment-client/src/AssignmentClient.cpp +++ b/assignment-client/src/AssignmentClient.cpp @@ -124,32 +124,36 @@ void AssignmentClient::readPendingDatagrams() { // construct the deployed assignment from the packet data _currentAssignment = AssignmentFactory::unpackAssignment(receivedPacket); - qDebug() << "Received an assignment -" << *_currentAssignment; - - // switch our nodelist domain IP and port to whoever sent us the assignment - - nodeList->setDomainSockAddr(senderSockAddr); - nodeList->setOwnerUUID(_currentAssignment->getUUID()); - - qDebug() << "Destination IP for assignment is" << nodeList->getDomainIP().toString(); - - // start the deployed assignment - QThread* workerThread = new QThread(this); - - connect(workerThread, SIGNAL(started()), _currentAssignment, SLOT(run())); - - connect(_currentAssignment, SIGNAL(finished()), this, SLOT(assignmentCompleted())); - connect(_currentAssignment, SIGNAL(finished()), workerThread, SLOT(quit())); - connect(_currentAssignment, SIGNAL(finished()), _currentAssignment, SLOT(deleteLater())); - connect(workerThread, SIGNAL(finished()), workerThread, SLOT(deleteLater())); - - _currentAssignment->moveToThread(workerThread); - - // move the NodeList to the thread used for the _current assignment - nodeList->moveToThread(workerThread); - - // Starts an event loop, and emits workerThread->started() - workerThread->start(); + if (_currentAssignment) { + qDebug() << "Received an assignment -" << *_currentAssignment; + + // switch our nodelist domain IP and port to whoever sent us the assignment + + nodeList->setDomainSockAddr(senderSockAddr); + nodeList->setOwnerUUID(_currentAssignment->getUUID()); + + qDebug() << "Destination IP for assignment is" << nodeList->getDomainIP().toString(); + + // start the deployed assignment + QThread* workerThread = new QThread(this); + + connect(workerThread, SIGNAL(started()), _currentAssignment, SLOT(run())); + + connect(_currentAssignment, SIGNAL(finished()), this, SLOT(assignmentCompleted())); + connect(_currentAssignment, SIGNAL(finished()), workerThread, SLOT(quit())); + connect(_currentAssignment, SIGNAL(finished()), _currentAssignment, SLOT(deleteLater())); + connect(workerThread, SIGNAL(finished()), workerThread, SLOT(deleteLater())); + + _currentAssignment->moveToThread(workerThread); + + // move the NodeList to the thread used for the _current assignment + nodeList->moveToThread(workerThread); + + // Starts an event loop, and emits workerThread->started() + workerThread->start(); + } else { + qDebug() << "Received an assignment that could not be unpacked. Re-requesting."; + } } } else { // have the NodeList attempt to handle it diff --git a/assignment-client/src/AssignmentFactory.cpp b/assignment-client/src/AssignmentFactory.cpp index 0b8e089c01..ef587c9b6d 100644 --- a/assignment-client/src/AssignmentFactory.cpp +++ b/assignment-client/src/AssignmentFactory.cpp @@ -21,10 +21,12 @@ ThreadedAssignment* AssignmentFactory::unpackAssignment(const QByteArray& packet) { int headerBytes = numBytesForPacketHeader(packet); - Assignment::Type assignmentType = Assignment::AllTypes; - memcpy(&assignmentType, packet.data() + headerBytes, sizeof(Assignment::Type)); + quint8 packedType; + memcpy(&packedType, packet.data() + headerBytes, sizeof(packedType)); - switch (assignmentType) { + Assignment::Type unpackedType = (Assignment::Type) packedType; + + switch (unpackedType) { case Assignment::AudioMixerType: return new AudioMixer(packet); case Assignment::AvatarMixerType: diff --git a/domain-server/src/DomainServer.cpp b/domain-server/src/DomainServer.cpp index 073f788f86..665ef45eb1 100644 --- a/domain-server/src/DomainServer.cpp +++ b/domain-server/src/DomainServer.cpp @@ -222,6 +222,7 @@ void DomainServer::readAvailableDatagrams() { if (assignmentToDeploy) { // give this assignment out, either the type matches or the requestor said they will take any assignmentPacket.resize(numAssignmentPacketHeaderBytes); + QDataStream assignmentStream(&assignmentPacket, QIODevice::Append); assignmentStream << *assignmentToDeploy; diff --git a/libraries/shared/src/Assignment.cpp b/libraries/shared/src/Assignment.cpp index 0040fd47a3..ca6a6adca7 100644 --- a/libraries/shared/src/Assignment.cpp +++ b/libraries/shared/src/Assignment.cpp @@ -70,6 +70,7 @@ Assignment::Assignment(Assignment::Command command, Assignment::Type type, const } Assignment::Assignment(const QByteArray& packet) : + _pool(), _location(GlobalLocation), _numberOfInstances(1), _payload() @@ -85,7 +86,9 @@ Assignment::Assignment(const QByteArray& packet) : QDataStream packetStream(packet); packetStream.skipRawData(numBytesForPacketHeader(packet)); - packetStream.readRawData(reinterpret_cast(&_type), sizeof(Assignment::Type)); + uchar assignmentType; + packetStream >> assignmentType; + _type = (Assignment::Type) assignmentType; if (_command != Assignment::RequestCommand) { // read the GUID for this assignment @@ -155,13 +158,13 @@ const char* Assignment::getTypeName() const { } QDebug operator<<(QDebug debug, const Assignment &assignment) { - debug.nospace() << "UUID: " << assignment.getUUID().toString().toStdString().c_str() << + debug.nospace() << "UUID: " << qPrintable(assignment.getUUID().toString()) << ", Type: " << assignment.getType(); return debug.nospace(); } QDataStream& operator<<(QDataStream &out, const Assignment& assignment) { - out << (char) assignment._type; + out << (quint8) assignment._type; // pack the UUID for this assignment, if this is an assignment create or deploy if (assignment._command != Assignment::RequestCommand) { diff --git a/libraries/shared/src/PacketHeaders.cpp b/libraries/shared/src/PacketHeaders.cpp index 529f2639d7..fc9511622f 100644 --- a/libraries/shared/src/PacketHeaders.cpp +++ b/libraries/shared/src/PacketHeaders.cpp @@ -16,7 +16,7 @@ #include "PacketHeaders.h" int arithmeticCodingValueFromBuffer(const char* checkValue) { - if (((int) *checkValue) < 255) { + if (((uchar) *checkValue) < 255) { return *checkValue; } else { return 255 + arithmeticCodingValueFromBuffer(checkValue + 1); @@ -24,8 +24,8 @@ int arithmeticCodingValueFromBuffer(const char* checkValue) { } int numBytesArithmeticCodingFromBuffer(const char* checkValue) { - if (((int) *checkValue) < 255) { - return *checkValue; + if (((uchar) *checkValue) < 255) { + return 1; } else { return 1 + numBytesArithmeticCodingFromBuffer(checkValue + 1); } @@ -50,13 +50,19 @@ PacketVersion versionForPacketType(PacketType type) { } } +const int MAX_HEADER_BYTES = sizeof(PacketType) + sizeof(PacketVersion) + NUM_BYTES_RFC4122_UUID; + QByteArray byteArrayWithPopluatedHeader(PacketType type, const QUuid& connectionUUID) { - QByteArray freshByteArray; - populatePacketHeader(freshByteArray, type, connectionUUID); + QByteArray freshByteArray(MAX_HEADER_BYTES, 0); + freshByteArray.resize(populatePacketHeader(freshByteArray, type, connectionUUID)); return freshByteArray; } int populatePacketHeader(QByteArray& packet, PacketType type, const QUuid& connectionUUID) { + if (packet.size() < MAX_HEADER_BYTES) { + packet.resize(numBytesForPacketHeaderGivenPacketType(type)); + } + return populatePacketHeader(packet.data(), type, connectionUUID); } @@ -110,7 +116,7 @@ int numBytesForPacketHeaderGivenPacketType(PacketType type) { } void deconstructPacketHeader(const QByteArray& packet, QUuid& senderUUID) { - senderUUID = QUuid::fromRfc4122(packet.mid(arithmeticCodingValueFromBuffer(packet.data()) + sizeof(PacketVersion))); + senderUUID = QUuid::fromRfc4122(packet.mid(numBytesArithmeticCodingFromBuffer(packet.data()) + sizeof(PacketVersion))); } PacketType packetTypeForPacket(const QByteArray& packet) { From 75e2fa491a08ed2110a8ef6b78e4844a5329f6f5 Mon Sep 17 00:00:00 2001 From: Stephen Birarda Date: Tue, 28 Jan 2014 11:26:36 -0800 Subject: [PATCH 04/16] some type fixes for marshalling/un-marshalling of data --- domain-server/src/DomainServer.cpp | 1 - libraries/shared/src/NodeList.cpp | 4 ++-- libraries/shared/src/NodeList.h | 2 +- libraries/shared/src/PacketHeaders.cpp | 2 +- 4 files changed, 4 insertions(+), 5 deletions(-) diff --git a/domain-server/src/DomainServer.cpp b/domain-server/src/DomainServer.cpp index 665ef45eb1..62ee855ddb 100644 --- a/domain-server/src/DomainServer.cpp +++ b/domain-server/src/DomainServer.cpp @@ -128,7 +128,6 @@ void DomainServer::readAvailableDatagrams() { deconstructPacketHeader(receivedPacket, nodeUUID); packetStream >> nodeType; - packetStream >> nodePublicAddress >> nodeLocalAddress; if (nodePublicAddress.getAddress().isNull()) { diff --git a/libraries/shared/src/NodeList.cpp b/libraries/shared/src/NodeList.cpp index 83e8d9824c..527840e0cd 100644 --- a/libraries/shared/src/NodeList.cpp +++ b/libraries/shared/src/NodeList.cpp @@ -464,11 +464,11 @@ void NodeList::sendDomainServerCheckIn() { // check in packet has header, optional UUID, node type, port, IP, node types of interest, null termination QByteArray domainServerPacket = byteArrayWithPopluatedHeader(PacketTypeDomainListRequest); QDataStream packetStream(&domainServerPacket, QIODevice::Append); - + // pack our data to send to the domain-server packetStream << _ownerType << _publicSockAddr << HifiSockAddr(QHostAddress(getHostOrderLocalAddress()), _nodeSocket.localPort()) - << (char) _nodeTypesOfInterest.size(); + << (quint8) _nodeTypesOfInterest.size(); // copy over the bytes for node types of interest, if required foreach (NODE_TYPE nodeTypeOfInterest, _nodeTypesOfInterest) { diff --git a/libraries/shared/src/NodeList.h b/libraries/shared/src/NodeList.h index 3f811dbad4..f978c5479e 100644 --- a/libraries/shared/src/NodeList.h +++ b/libraries/shared/src/NodeList.h @@ -146,7 +146,7 @@ private: QString _domainHostname; HifiSockAddr _domainSockAddr; QUdpSocket _nodeSocket; - char _ownerType; + NODE_TYPE _ownerType; QSet _nodeTypesOfInterest; QUuid _ownerUUID; int _numNoReplyDomainCheckIns; diff --git a/libraries/shared/src/PacketHeaders.cpp b/libraries/shared/src/PacketHeaders.cpp index fc9511622f..a725198748 100644 --- a/libraries/shared/src/PacketHeaders.cpp +++ b/libraries/shared/src/PacketHeaders.cpp @@ -34,7 +34,7 @@ int numBytesArithmeticCodingFromBuffer(const char* checkValue) { int packArithmeticallyCodedValue(int value, char* destination) { if (value < 255) { // less than 255, just pack our value - destination[0] = (char) value; + destination[0] = (uchar) value; return 1; } else { // pack 255 and then recursively pack on From ffefc529f3c5a7d9afec4c8703bc8b81e6a0f5f4 Mon Sep 17 00:00:00 2001 From: Stephen Birarda Date: Tue, 28 Jan 2014 11:53:09 -0800 Subject: [PATCH 05/16] ensure UUID pulled from packet header is exactly 16 bytes --- domain-server/src/DomainServer.cpp | 1 + libraries/shared/src/NodeList.cpp | 2 +- libraries/shared/src/PacketHeaders.cpp | 8 ++++---- 3 files changed, 6 insertions(+), 5 deletions(-) diff --git a/domain-server/src/DomainServer.cpp b/domain-server/src/DomainServer.cpp index 62ee855ddb..5cffc724f3 100644 --- a/domain-server/src/DomainServer.cpp +++ b/domain-server/src/DomainServer.cpp @@ -127,6 +127,7 @@ void DomainServer::readAvailableDatagrams() { packetStream.skipRawData(numBytesForPacketHeader(receivedPacket)); deconstructPacketHeader(receivedPacket, nodeUUID); + packetStream >> nodeType; packetStream >> nodePublicAddress >> nodeLocalAddress; diff --git a/libraries/shared/src/NodeList.cpp b/libraries/shared/src/NodeList.cpp index 527840e0cd..a2ad00125e 100644 --- a/libraries/shared/src/NodeList.cpp +++ b/libraries/shared/src/NodeList.cpp @@ -474,7 +474,7 @@ void NodeList::sendDomainServerCheckIn() { foreach (NODE_TYPE nodeTypeOfInterest, _nodeTypesOfInterest) { packetStream << nodeTypeOfInterest; } - + _nodeSocket.writeDatagram(domainServerPacket, _domainSockAddr.getAddress(), _domainSockAddr.getPort()); const int NUM_DOMAIN_SERVER_CHECKINS_PER_STUN_REQUEST = 5; static unsigned int numDomainCheckins = 0; diff --git a/libraries/shared/src/PacketHeaders.cpp b/libraries/shared/src/PacketHeaders.cpp index a725198748..545c779fea 100644 --- a/libraries/shared/src/PacketHeaders.cpp +++ b/libraries/shared/src/PacketHeaders.cpp @@ -59,7 +59,7 @@ QByteArray byteArrayWithPopluatedHeader(PacketType type, const QUuid& connection } int populatePacketHeader(QByteArray& packet, PacketType type, const QUuid& connectionUUID) { - if (packet.size() < MAX_HEADER_BYTES) { + if (packet.size() < numBytesForPacketHeaderGivenPacketType(type)) { packet.resize(numBytesForPacketHeaderGivenPacketType(type)); } @@ -77,7 +77,6 @@ int populatePacketHeader(char* packet, PacketType type, const QUuid& connectionU // return the number of bytes written for pointer pushing return numTypeBytes + sizeof(PacketVersion) + NUM_BYTES_RFC4122_UUID; - } bool packetVersionMatch(const QByteArray& packet) { @@ -112,11 +111,12 @@ int numBytesForPacketHeader(const char* packet) { } int numBytesForPacketHeaderGivenPacketType(PacketType type) { - return (int) ceilf((float)type) + sizeof(PacketVersion) + NUM_BYTES_RFC4122_UUID; + return (int) ceilf((float)type / 255) + sizeof(PacketVersion) + NUM_BYTES_RFC4122_UUID; } void deconstructPacketHeader(const QByteArray& packet, QUuid& senderUUID) { - senderUUID = QUuid::fromRfc4122(packet.mid(numBytesArithmeticCodingFromBuffer(packet.data()) + sizeof(PacketVersion))); + senderUUID = QUuid::fromRfc4122(packet.mid(numBytesArithmeticCodingFromBuffer(packet.data()) + sizeof(PacketVersion), + NUM_BYTES_RFC4122_UUID)); } PacketType packetTypeForPacket(const QByteArray& packet) { From b009cd8e6766302330d87dde2d6749cb603f05ab Mon Sep 17 00:00:00 2001 From: Stephen Birarda Date: Tue, 28 Jan 2014 12:25:44 -0800 Subject: [PATCH 06/16] repair more node communication problems after refactor --- interface/src/DatagramProcessor.cpp | 3 ++- libraries/shared/src/Assignment.cpp | 5 ++--- libraries/shared/src/Node.cpp | 4 ++-- libraries/shared/src/Node.h | 4 ++-- libraries/shared/src/NodeList.cpp | 11 ++++------- 5 files changed, 12 insertions(+), 15 deletions(-) diff --git a/interface/src/DatagramProcessor.cpp b/interface/src/DatagramProcessor.cpp index e2437e4441..3e4347fc98 100644 --- a/interface/src/DatagramProcessor.cpp +++ b/interface/src/DatagramProcessor.cpp @@ -34,7 +34,8 @@ void DatagramProcessor::processDatagrams() { while (NodeList::getInstance()->getNodeSocket().hasPendingDatagrams()) { incomingPacket.resize(nodeList->getNodeSocket().pendingDatagramSize()); - nodeList->getNodeSocket().readDatagram(incomingPacket.data(), incomingPacket.size()); + nodeList->getNodeSocket().readDatagram(incomingPacket.data(), incomingPacket.size(), + senderSockAddr.getAddressPointer(), senderSockAddr.getPortPointer()); _packetCount++; _byteCount += incomingPacket.size(); diff --git a/libraries/shared/src/Assignment.cpp b/libraries/shared/src/Assignment.cpp index ca6a6adca7..5432278b17 100644 --- a/libraries/shared/src/Assignment.cpp +++ b/libraries/shared/src/Assignment.cpp @@ -46,11 +46,12 @@ Assignment::Assignment() : _uuid(), _command(Assignment::RequestCommand), _type(Assignment::AllTypes), + _pool(), _location(Assignment::LocalLocation), _numberOfInstances(1), _payload() { - setPool(NULL); + } Assignment::Assignment(Assignment::Command command, Assignment::Type type, const QString& pool, Assignment::Location location) : @@ -65,8 +66,6 @@ Assignment::Assignment(Assignment::Command command, Assignment::Type type, const // this is a newly created assignment, generate a random UUID _uuid = QUuid::createUuid(); } - - setPool(pool); } Assignment::Assignment(const QByteArray& packet) : diff --git a/libraries/shared/src/Node.cpp b/libraries/shared/src/Node.cpp index 37628fb649..18367019ad 100644 --- a/libraries/shared/src/Node.cpp +++ b/libraries/shared/src/Node.cpp @@ -134,7 +134,7 @@ float Node::getAverageKilobitsPerSecond() { } } -QDataStream& operator>>(QDataStream& out, const Node& node) { +QDataStream& operator<<(QDataStream& out, const Node& node) { out << node._type; out << node._uuid; out << node._publicSocket; @@ -143,7 +143,7 @@ QDataStream& operator>>(QDataStream& out, const Node& node) { return out; } -QDataStream& operator<<(QDataStream& in, Node& node) { +QDataStream& operator>>(QDataStream& in, Node& node) { in >> node._type; in >> node._uuid; in >> node._publicSocket; diff --git a/libraries/shared/src/Node.h b/libraries/shared/src/Node.h index eacbc93892..15dfd633b1 100644 --- a/libraries/shared/src/Node.h +++ b/libraries/shared/src/Node.h @@ -88,8 +88,8 @@ public: void setClockSkewUsec(int clockSkew) { _clockSkewUsec = clockSkew; } QMutex& getMutex() { return _mutex; } - friend QDataStream& operator>>(QDataStream& out, const Node& node); - friend QDataStream& operator<<(QDataStream& in, Node& node); + friend QDataStream& operator<<(QDataStream& out, const Node& node); + friend QDataStream& operator>>(QDataStream& in, Node& node); private: // privatize copy and assignment operator to disallow Node copying diff --git a/libraries/shared/src/NodeList.cpp b/libraries/shared/src/NodeList.cpp index a2ad00125e..f2710965f5 100644 --- a/libraries/shared/src/NodeList.cpp +++ b/libraries/shared/src/NodeList.cpp @@ -506,7 +506,7 @@ int NodeList::processDomainServerList(const QByteArray& packet) { QDataStream packetStream(packet); packetStream.skipRawData(numBytesForPacketHeader(packet)); - while(!packetStream.atEnd()) { + while(packetStream.device()->pos() < packet.size()) { packetStream >> nodeType >> nodeUUID >> nodePublicSocket >> nodeLocalSocket; // if the public socket address is 0 then it's reachable at the same IP @@ -551,14 +551,11 @@ QByteArray NodeList::constructPingPacket() { } QByteArray NodeList::constructPingReplyPacket(const QByteArray& pingPacket) { - QByteArray replyPacket; - uint64_t timeFromOriginalPing; memcpy(&timeFromOriginalPing, pingPacket.data() + numBytesForPacketHeader(pingPacket), sizeof(timeFromOriginalPing)); - QDataStream packetStream(replyPacket); - - packetStream.device()->seek(populatePacketHeader(replyPacket, PacketTypePingReply)); + QByteArray replyPacket = byteArrayWithPopluatedHeader(PacketTypePingReply); + QDataStream packetStream(&replyPacket, QIODevice::Append); packetStream << timeFromOriginalPing << usecTimestampNow(); @@ -574,7 +571,7 @@ void NodeList::pingPublicAndLocalSocketsForInactiveNode(Node* node) { } SharedNodePointer NodeList::addOrUpdateNode(const QUuid& uuid, char nodeType, - const HifiSockAddr& publicSocket, const HifiSockAddr& localSocket) { + const HifiSockAddr& publicSocket, const HifiSockAddr& localSocket) { _nodeHashMutex.lock(); SharedNodePointer matchingNode = _nodeHash.value(uuid); From 3a706a2759e55bb0af1f6a8bd1f1147f28712cca Mon Sep 17 00:00:00 2001 From: Stephen Birarda Date: Tue, 28 Jan 2014 12:31:25 -0800 Subject: [PATCH 07/16] repair the count of avatars and servers --- interface/src/Application.cpp | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/interface/src/Application.cpp b/interface/src/Application.cpp index cda34f727c..4b293f6f46 100644 --- a/interface/src/Application.cpp +++ b/interface/src/Application.cpp @@ -3148,10 +3148,8 @@ void Application::displayStats() { glPointSize(1.0f); - int totalAvatars = 0, totalServers = 0; - foreach (const SharedNodePointer& node, NodeList::getInstance()->getNodeHash()) { - node->getType() == NODE_TYPE_AGENT ? totalAvatars++ : totalServers++; - } + int totalAvatars = _avatarManager.size(); + int totalServers = NodeList::getInstance()->size(); if (mirrorEnabled) { horizontalOffset += MIRROR_VIEW_WIDTH + MIRROR_VIEW_LEFT_PADDING * 2; From 7b4921e7616c21e8197b996d56ca44d605b3368b Mon Sep 17 00:00:00 2001 From: Stephen Birarda Date: Tue, 28 Jan 2014 12:34:08 -0800 Subject: [PATCH 08/16] use quint64 in place of uint64_t for QDataStream --- libraries/shared/src/NodeList.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libraries/shared/src/NodeList.cpp b/libraries/shared/src/NodeList.cpp index f2710965f5..5fcd4d4460 100644 --- a/libraries/shared/src/NodeList.cpp +++ b/libraries/shared/src/NodeList.cpp @@ -551,7 +551,7 @@ QByteArray NodeList::constructPingPacket() { } QByteArray NodeList::constructPingReplyPacket(const QByteArray& pingPacket) { - uint64_t timeFromOriginalPing; + quint64 timeFromOriginalPing; memcpy(&timeFromOriginalPing, pingPacket.data() + numBytesForPacketHeader(pingPacket), sizeof(timeFromOriginalPing)); QByteArray replyPacket = byteArrayWithPopluatedHeader(PacketTypePingReply); From cda06d1cb36ffe36866b0e40a86c0dca0530cc84 Mon Sep 17 00:00:00 2001 From: Stephen Birarda Date: Tue, 28 Jan 2014 12:35:42 -0800 Subject: [PATCH 09/16] replace uint64_t with quint64 for Qt friendlyness --- animation-server/src/AnimationServer.cpp | 10 +-- domain-server/src/DomainServer.cpp | 2 +- interface/src/Application.cpp | 4 +- interface/src/Application.h | 2 +- interface/src/VoxelHideShowThread.cpp | 16 ++-- interface/src/VoxelSystem.cpp | 20 ++--- interface/src/VoxelSystem.h | 8 +- interface/src/avatar/Profile.cpp | 6 +- interface/src/avatar/Profile.h | 2 +- interface/src/devices/Faceshift.cpp | 2 +- interface/src/devices/Faceshift.h | 2 +- interface/src/devices/SixenseManager.h | 2 +- interface/src/starfield/Config.h | 2 +- libraries/avatars/src/AvatarData.h | 2 +- libraries/avatars/src/HandData.h | 2 +- .../src/OctreeInboundPacketProcessor.cpp | 24 +++--- .../src/OctreeInboundPacketProcessor.h | 52 ++++++------- .../octree-server/src/OctreeQueryNode.cpp | 4 +- libraries/octree-server/src/OctreeQueryNode.h | 8 +- .../octree-server/src/OctreeSendThread.cpp | 34 ++++---- .../octree-server/src/OctreeSendThread.h | 10 +-- libraries/octree-server/src/OctreeServer.cpp | 34 ++++---- libraries/octree-server/src/OctreeServer.h | 4 +- libraries/octree/src/Octree.cpp | 2 +- libraries/octree/src/Octree.h | 6 +- libraries/octree/src/OctreeConstants.h | 2 +- .../octree/src/OctreeEditPacketSender.cpp | 14 ++-- libraries/octree/src/OctreeElement.cpp | 62 +++++++-------- libraries/octree/src/OctreeElement.h | 78 +++++++++---------- libraries/octree/src/OctreePacketData.cpp | 18 ++--- libraries/octree/src/OctreePacketData.h | 30 +++---- libraries/octree/src/OctreePersistThread.cpp | 14 ++-- libraries/octree/src/OctreePersistThread.h | 6 +- libraries/octree/src/OctreeQuery.h | 2 +- libraries/octree/src/OctreeSceneStats.cpp | 2 +- libraries/octree/src/OctreeSceneStats.h | 14 ++-- .../particle-server/src/ParticleNodeData.h | 6 +- .../particle-server/src/ParticleServer.cpp | 10 +-- libraries/particles/src/Particle.cpp | 20 ++--- libraries/particles/src/Particle.h | 16 ++-- libraries/particles/src/ParticleTree.cpp | 18 ++--- libraries/particles/src/ParticleTree.h | 8 +- libraries/shared/src/Node.h | 12 +-- libraries/shared/src/NodeList.cpp | 2 +- libraries/shared/src/NodeList.h | 6 +- libraries/shared/src/PacketSender.cpp | 24 +++--- libraries/shared/src/PacketSender.h | 30 +++---- libraries/shared/src/PerfStat.cpp | 4 +- libraries/shared/src/PerfStat.h | 8 +- libraries/shared/src/Radix2IntegerScanner.h | 2 +- .../shared/src/ReceivedPacketProcessor.cpp | 2 +- libraries/shared/src/SharedUtil.cpp | 4 +- libraries/shared/src/SharedUtil.h | 10 +-- libraries/shared/src/SimpleMovingAverage.h | 2 +- libraries/voxels/src/VoxelConstants.h | 2 +- .../voxels/src/VoxelEditPacketSender.cpp | 4 +- libraries/voxels/src/VoxelPacketData.h | 2 +- 57 files changed, 347 insertions(+), 347 deletions(-) diff --git a/animation-server/src/AnimationServer.cpp b/animation-server/src/AnimationServer.cpp index c436fd1d4b..52c281c0d9 100644 --- a/animation-server/src/AnimationServer.cpp +++ b/animation-server/src/AnimationServer.cpp @@ -591,8 +591,8 @@ double start = 0; void* animateVoxels(void* args) { - uint64_t lastAnimateTime = 0; - uint64_t lastProcessTime = 0; + quint64 lastAnimateTime = 0; + quint64 lastProcessTime = 0; int processesPerAnimate = 0; bool firstTime = true; @@ -622,8 +622,8 @@ void* animateVoxels(void* args) { // The while loop will be running at PROCESSING_FPS, but we only want to call these animation functions at // ANIMATE_FPS. So we check out last animate time and only call these if we've elapsed that time. - uint64_t now = usecTimestampNow(); - uint64_t animationElapsed = now - lastAnimateTime; + quint64 now = usecTimestampNow(); + quint64 animationElapsed = now - lastAnimateTime; int withinAnimationTarget = ANIMATE_VOXELS_INTERVAL_USECS - animationElapsed; const int CLOSE_ENOUGH_TO_ANIMATE = 2000; // approximately 2 ms @@ -676,7 +676,7 @@ void* animateVoxels(void* args) { processesPerAnimate++; } // dynamically sleep until we need to fire off the next set of voxels - uint64_t usecToSleep = PROCESSING_INTERVAL_USECS - (usecTimestampNow() - lastProcessTime); + quint64 usecToSleep = PROCESSING_INTERVAL_USECS - (usecTimestampNow() - lastProcessTime); if (usecToSleep > PROCESSING_INTERVAL_USECS) { usecToSleep = PROCESSING_INTERVAL_USECS; } diff --git a/domain-server/src/DomainServer.cpp b/domain-server/src/DomainServer.cpp index 5cffc724f3..908f0bacdf 100644 --- a/domain-server/src/DomainServer.cpp +++ b/domain-server/src/DomainServer.cpp @@ -201,7 +201,7 @@ void DomainServer::readAvailableDatagrams() { } // update last receive to now - uint64_t timeNow = usecTimestampNow(); + quint64 timeNow = usecTimestampNow(); checkInNode->setLastHeardMicrostamp(timeNow); // send the constructed list back to this node diff --git a/interface/src/Application.cpp b/interface/src/Application.cpp index 4b293f6f46..892b97521a 100644 --- a/interface/src/Application.cpp +++ b/interface/src/Application.cpp @@ -2256,7 +2256,7 @@ void Application::updateCursor(float deltaTime) { // watch mouse position, if it hasn't moved, hide the cursor bool underMouse = _glWidget->underMouse(); if (!_mouseHidden) { - uint64_t now = usecTimestampNow(); + quint64 now = usecTimestampNow(); int elapsed = now - _lastMouseMove; const int HIDE_CURSOR_TIMEOUT = 1 * 1000 * 1000; // 1 second if (elapsed > HIDE_CURSOR_TIMEOUT && (underMouse || !_seenMouseMove)) { @@ -3057,7 +3057,7 @@ void Application::displayOverlay() { // Show on-screen msec timer if (Menu::getInstance()->isOptionChecked(MenuOption::FrameTimer)) { char frameTimer[10]; - uint64_t mSecsNow = floor(usecTimestampNow() / 1000.0 + 0.5); + quint64 mSecsNow = floor(usecTimestampNow() / 1000.0 + 0.5); sprintf(frameTimer, "%d\n", (int)(mSecsNow % 1000)); int timerBottom = (Menu::getInstance()->isOptionChecked(MenuOption::Stats) && diff --git a/interface/src/Application.h b/interface/src/Application.h index 3645355b89..dae7d83da5 100644 --- a/interface/src/Application.h +++ b/interface/src/Application.h @@ -403,7 +403,7 @@ private: int _mouseY; int _mouseDragStartedX; int _mouseDragStartedY; - uint64_t _lastMouseMove; + quint64 _lastMouseMove; bool _mouseHidden; bool _seenMouseMove; diff --git a/interface/src/VoxelHideShowThread.cpp b/interface/src/VoxelHideShowThread.cpp index 2a42db7f70..d7a25b4b6d 100644 --- a/interface/src/VoxelHideShowThread.cpp +++ b/interface/src/VoxelHideShowThread.cpp @@ -21,15 +21,15 @@ VoxelHideShowThread::VoxelHideShowThread(VoxelSystem* theSystem) : } bool VoxelHideShowThread::process() { - const uint64_t MSECS_TO_USECS = 1000; - const uint64_t SECS_TO_USECS = 1000 * MSECS_TO_USECS; - const uint64_t FRAME_RATE = 60; - const uint64_t USECS_PER_FRAME = SECS_TO_USECS / FRAME_RATE; // every 60fps + const quint64 MSECS_TO_USECS = 1000; + const quint64 SECS_TO_USECS = 1000 * MSECS_TO_USECS; + const quint64 FRAME_RATE = 60; + const quint64 USECS_PER_FRAME = SECS_TO_USECS / FRAME_RATE; // every 60fps - uint64_t start = usecTimestampNow(); + quint64 start = usecTimestampNow(); _theSystem->checkForCulling(); - uint64_t end = usecTimestampNow(); - uint64_t elapsed = end - start; + quint64 end = usecTimestampNow(); + quint64 elapsed = end - start; bool showExtraDebugging = Application::getInstance()->getLogger()->extraDebugging(); if (showExtraDebugging && elapsed > USECS_PER_FRAME) { @@ -38,7 +38,7 @@ bool VoxelHideShowThread::process() { if (isStillRunning()) { if (elapsed < USECS_PER_FRAME) { - uint64_t sleepFor = USECS_PER_FRAME - elapsed; + quint64 sleepFor = USECS_PER_FRAME - elapsed; usleep(sleepFor); } } diff --git a/interface/src/VoxelSystem.cpp b/interface/src/VoxelSystem.cpp index 029690e56a..a663c27ce2 100644 --- a/interface/src/VoxelSystem.cpp +++ b/interface/src/VoxelSystem.cpp @@ -638,8 +638,8 @@ void VoxelSystem::setupNewVoxelsForDrawing() { return; // bail early if we're not initialized } - uint64_t start = usecTimestampNow(); - uint64_t sinceLastTime = (start - _setupNewVoxelsForDrawingLastFinished) / 1000; + quint64 start = usecTimestampNow(); + quint64 sinceLastTime = (start - _setupNewVoxelsForDrawingLastFinished) / 1000; bool iAmDebugging = false; // if you're debugging set this to true, so you won't get skipped for slow debugging if (!iAmDebugging && sinceLastTime <= std::max((float) _setupNewVoxelsForDrawingLastElapsed, SIXTY_FPS_IN_MILLISECONDS)) { @@ -685,7 +685,7 @@ void VoxelSystem::setupNewVoxelsForDrawing() { _bufferWriteLock.unlock(); - uint64_t end = usecTimestampNow(); + quint64 end = usecTimestampNow(); int elapsedmsec = (end - start) / 1000; _setupNewVoxelsForDrawingLastFinished = end; _setupNewVoxelsForDrawingLastElapsed = elapsedmsec; @@ -702,8 +702,8 @@ void VoxelSystem::setupNewVoxelsForDrawingSingleNode(bool allowBailEarly) { PerformanceWarning warn(Menu::getInstance()->isOptionChecked(MenuOption::PipelineWarnings), "setupNewVoxelsForDrawingSingleNode() xxxxx"); - uint64_t start = usecTimestampNow(); - uint64_t sinceLastTime = (start - _setupNewVoxelsForDrawingLastFinished) / 1000; + quint64 start = usecTimestampNow(); + quint64 sinceLastTime = (start - _setupNewVoxelsForDrawingLastFinished) / 1000; bool iAmDebugging = false; // if you're debugging set this to true, so you won't get skipped for slow debugging if (allowBailEarly && !iAmDebugging && @@ -728,7 +728,7 @@ void VoxelSystem::setupNewVoxelsForDrawingSingleNode(bool allowBailEarly) { _bufferWriteLock.unlock(); - uint64_t end = usecTimestampNow(); + quint64 end = usecTimestampNow(); int elapsedmsec = (end - start) / 1000; _setupNewVoxelsForDrawingLastFinished = end; _setupNewVoxelsForDrawingLastElapsed = elapsedmsec; @@ -737,14 +737,14 @@ void VoxelSystem::setupNewVoxelsForDrawingSingleNode(bool allowBailEarly) { void VoxelSystem::checkForCulling() { PerformanceWarning warn(Menu::getInstance()->isOptionChecked(MenuOption::PipelineWarnings), "checkForCulling()"); - uint64_t start = usecTimestampNow(); + quint64 start = usecTimestampNow(); // track how long its been since we were last moving. If we have recently moved then only use delta frustums, if // it's been a long time since we last moved, then go ahead and do a full frustum cull. if (isViewChanging()) { _lastViewIsChanging = start; } - uint64_t sinceLastMoving = (start - _lastViewIsChanging) / 1000; + quint64 sinceLastMoving = (start - _lastViewIsChanging) / 1000; bool enoughTime = (sinceLastMoving >= std::max((float) _lastViewCullingElapsed, VIEW_CULLING_RATE_IN_MILLISECONDS)); // These has changed events will occur before we stop. So we need to remember this for when we finally have stopped @@ -766,7 +766,7 @@ void VoxelSystem::checkForCulling() { hideOutOfView(forceFullFrustum); if (forceFullFrustum) { - uint64_t endViewCulling = usecTimestampNow(); + quint64 endViewCulling = usecTimestampNow(); _lastViewCullingElapsed = (endViewCulling - start) / 1000; } @@ -775,7 +775,7 @@ void VoxelSystem::checkForCulling() { // VBO reubuilding. Possibly we should do this only if our actual VBO usage crosses some lower boundary. cleanupRemovedVoxels(); - uint64_t sinceLastAudit = (start - _lastAudit) / 1000; + quint64 sinceLastAudit = (start - _lastAudit) / 1000; if (Menu::getInstance()->isOptionChecked(MenuOption::AutomaticallyAuditTree)) { if (sinceLastAudit >= std::max((float) _lastViewCullingElapsed, VIEW_CULLING_RATE_IN_MILLISECONDS)) { diff --git a/interface/src/VoxelSystem.h b/interface/src/VoxelSystem.h index 915b5a05b4..ca90424b70 100644 --- a/interface/src/VoxelSystem.h +++ b/interface/src/VoxelSystem.h @@ -229,10 +229,10 @@ private: bool _readRenderFullVBO; int _setupNewVoxelsForDrawingLastElapsed; - uint64_t _setupNewVoxelsForDrawingLastFinished; - uint64_t _lastViewCulling; - uint64_t _lastViewIsChanging; - uint64_t _lastAudit; + quint64 _setupNewVoxelsForDrawingLastFinished; + quint64 _lastViewCulling; + quint64 _lastViewIsChanging; + quint64 _lastAudit; int _lastViewCullingElapsed; bool _hasRecentlyChanged; diff --git a/interface/src/avatar/Profile.cpp b/interface/src/avatar/Profile.cpp index 83105f3f41..74f47bd658 100644 --- a/interface/src/avatar/Profile.cpp +++ b/interface/src/avatar/Profile.cpp @@ -87,7 +87,7 @@ void Profile::updatePosition(const glm::vec3 position) { if (_lastPosition != position) { static timeval lastPositionSend = {}; - const uint64_t DATA_SERVER_POSITION_UPDATE_INTERVAL_USECS = 5 * 1000 * 1000; + const quint64 DATA_SERVER_POSITION_UPDATE_INTERVAL_USECS = 5 * 1000 * 1000; const float DATA_SERVER_POSITION_CHANGE_THRESHOLD_METERS = 1; if (usecTimestampNow() - usecTimestamp(&lastPositionSend) >= DATA_SERVER_POSITION_UPDATE_INTERVAL_USECS && @@ -115,10 +115,10 @@ void Profile::updateOrientation(const glm::quat& orientation) { if (_lastOrientation == eulerAngles) { return; } - const uint64_t DATA_SERVER_ORIENTATION_UPDATE_INTERVAL_USECS = 5 * 1000 * 1000; + const quint64 DATA_SERVER_ORIENTATION_UPDATE_INTERVAL_USECS = 5 * 1000 * 1000; const float DATA_SERVER_ORIENTATION_CHANGE_THRESHOLD_DEGREES = 5.0f; - uint64_t now = usecTimestampNow(); + quint64 now = usecTimestampNow(); if (now - _lastOrientationSend >= DATA_SERVER_ORIENTATION_UPDATE_INTERVAL_USECS && glm::distance(_lastOrientation, eulerAngles) >= DATA_SERVER_ORIENTATION_CHANGE_THRESHOLD_DEGREES) { DataServerClient::putValueForKeyAndUserString(DataServerKey::Orientation, QString(createByteArray(eulerAngles)), diff --git a/interface/src/avatar/Profile.h b/interface/src/avatar/Profile.h index 225022b99d..5cb2295f5b 100644 --- a/interface/src/avatar/Profile.h +++ b/interface/src/avatar/Profile.h @@ -57,7 +57,7 @@ private: QString _lastDomain; glm::vec3 _lastPosition; glm::vec3 _lastOrientation; - uint64_t _lastOrientationSend; + quint64 _lastOrientationSend; QUrl _faceModelURL; QUrl _skeletonModelURL; }; diff --git a/interface/src/devices/Faceshift.cpp b/interface/src/devices/Faceshift.cpp index 437a3268d2..60839c362d 100644 --- a/interface/src/devices/Faceshift.cpp +++ b/interface/src/devices/Faceshift.cpp @@ -56,7 +56,7 @@ Faceshift::Faceshift() : } bool Faceshift::isActive() const { - const uint64_t ACTIVE_TIMEOUT_USECS = 1000000; + const quint64 ACTIVE_TIMEOUT_USECS = 1000000; return (usecTimestampNow() - _lastTrackingStateReceived) < ACTIVE_TIMEOUT_USECS; } diff --git a/interface/src/devices/Faceshift.h b/interface/src/devices/Faceshift.h index 62eb494f42..d3981fc182 100644 --- a/interface/src/devices/Faceshift.h +++ b/interface/src/devices/Faceshift.h @@ -90,7 +90,7 @@ private: bool _tcpEnabled; int _tcpRetryCount; bool _tracking; - uint64_t _lastTrackingStateReceived; + quint64 _lastTrackingStateReceived; glm::quat _headRotation; glm::vec3 _headAngularVelocity; diff --git a/interface/src/devices/SixenseManager.h b/interface/src/devices/SixenseManager.h index 863db7852f..1d8263ee30 100644 --- a/interface/src/devices/SixenseManager.h +++ b/interface/src/devices/SixenseManager.h @@ -25,7 +25,7 @@ public slots: private: - uint64_t _lastMovement; + quint64 _lastMovement; }; #endif /* defined(__interface__SixenseManager__) */ diff --git a/interface/src/starfield/Config.h b/interface/src/starfield/Config.h index 564f6f3a1a..04a5331cf0 100755 --- a/interface/src/starfield/Config.h +++ b/interface/src/starfield/Config.h @@ -59,7 +59,7 @@ namespace starfield { using namespace std; typedef uint32_t nuint; - typedef uint64_t wuint; + typedef quint64 wuint; } diff --git a/libraries/avatars/src/AvatarData.h b/libraries/avatars/src/AvatarData.h index bc16f2baaa..828f0a4bea 100755 --- a/libraries/avatars/src/AvatarData.h +++ b/libraries/avatars/src/AvatarData.h @@ -19,7 +19,7 @@ typedef unsigned char uint8_t; typedef unsigned short uint16_t; typedef unsigned int uint32_t; typedef signed long long int64_t; -typedef unsigned long long uint64_t; +typedef unsigned long long quint64; #define PRId64 "I64d" #else #include diff --git a/libraries/avatars/src/HandData.h b/libraries/avatars/src/HandData.h index 5c0a01540d..550c62e829 100755 --- a/libraries/avatars/src/HandData.h +++ b/libraries/avatars/src/HandData.h @@ -228,7 +228,7 @@ private: bool _isCollidingWithVoxel; /// Whether the finger of this palm is inside a leaf voxel bool _isCollidingWithPalm; - uint64_t _collisionlessPaddleExpiry; /// Timestamp after which paddle starts colliding + quint64 _collisionlessPaddleExpiry; /// Timestamp after which paddle starts colliding }; #endif /* defined(__hifi__HandData__) */ diff --git a/libraries/octree-server/src/OctreeInboundPacketProcessor.cpp b/libraries/octree-server/src/OctreeInboundPacketProcessor.cpp index fd5e9f1749..f9523851b4 100644 --- a/libraries/octree-server/src/OctreeInboundPacketProcessor.cpp +++ b/libraries/octree-server/src/OctreeInboundPacketProcessor.cpp @@ -61,12 +61,12 @@ void OctreeInboundPacketProcessor::processPacket(const HifiSockAddr& senderSockA const unsigned char* packetData = reinterpret_cast(packet.data()); unsigned short int sequence = (*((unsigned short int*)(packetData + numBytesPacketHeader))); - uint64_t sentAt = (*((uint64_t*)(packetData + numBytesPacketHeader + sizeof(sequence)))); - uint64_t arrivedAt = usecTimestampNow(); - uint64_t transitTime = arrivedAt - sentAt; + quint64 sentAt = (*((quint64*)(packetData + numBytesPacketHeader + sizeof(sequence)))); + quint64 arrivedAt = usecTimestampNow(); + quint64 transitTime = arrivedAt - sentAt; int editsInPacket = 0; - uint64_t processTime = 0; - uint64_t lockWaitTime = 0; + quint64 processTime = 0; + quint64 lockWaitTime = 0; if (_myServer->wantsDebugReceiving()) { qDebug() << "PROCESSING THREAD: got '" << packetType << "' packet - " << _receivedPacketCount @@ -84,19 +84,19 @@ void OctreeInboundPacketProcessor::processPacket(const HifiSockAddr& senderSockA packetType, packetData, packet.size(), editData, atByte, maxSize); } - uint64_t startLock = usecTimestampNow(); + quint64 startLock = usecTimestampNow(); _myServer->getOctree()->lockForWrite(); - uint64_t startProcess = usecTimestampNow(); + quint64 startProcess = usecTimestampNow(); int editDataBytesRead = _myServer->getOctree()->processEditPacketData(packetType, reinterpret_cast(packet.data()), packet.size(), editData, maxSize, senderNode.data()); _myServer->getOctree()->unlock(); - uint64_t endProcess = usecTimestampNow(); + quint64 endProcess = usecTimestampNow(); editsInPacket++; - uint64_t thisProcessTime = endProcess - startProcess; - uint64_t thisLockWaitTime = startProcess - startLock; + quint64 thisProcessTime = endProcess - startProcess; + quint64 thisLockWaitTime = startProcess - startLock; processTime += thisProcessTime; lockWaitTime += thisLockWaitTime; @@ -130,8 +130,8 @@ void OctreeInboundPacketProcessor::processPacket(const HifiSockAddr& senderSockA } } -void OctreeInboundPacketProcessor::trackInboundPackets(const QUuid& nodeUUID, int sequence, uint64_t transitTime, - int editsInPacket, uint64_t processTime, uint64_t lockWaitTime) { +void OctreeInboundPacketProcessor::trackInboundPackets(const QUuid& nodeUUID, int sequence, quint64 transitTime, + int editsInPacket, quint64 processTime, quint64 lockWaitTime) { _totalTransitTime += transitTime; _totalProcessTime += processTime; diff --git a/libraries/octree-server/src/OctreeInboundPacketProcessor.h b/libraries/octree-server/src/OctreeInboundPacketProcessor.h index a4d40e8ae1..3d9b12f484 100644 --- a/libraries/octree-server/src/OctreeInboundPacketProcessor.h +++ b/libraries/octree-server/src/OctreeInboundPacketProcessor.h @@ -20,21 +20,21 @@ class SingleSenderStats { public: SingleSenderStats(); - uint64_t getAverageTransitTimePerPacket() const { return _totalPackets == 0 ? 0 : _totalTransitTime / _totalPackets; } - uint64_t getAverageProcessTimePerPacket() const { return _totalPackets == 0 ? 0 : _totalProcessTime / _totalPackets; } - uint64_t getAverageLockWaitTimePerPacket() const { return _totalPackets == 0 ? 0 : _totalLockWaitTime / _totalPackets; } - uint64_t getTotalElementsProcessed() const { return _totalElementsInPacket; } - uint64_t getTotalPacketsProcessed() const { return _totalPackets; } - uint64_t getAverageProcessTimePerElement() const + quint64 getAverageTransitTimePerPacket() const { return _totalPackets == 0 ? 0 : _totalTransitTime / _totalPackets; } + quint64 getAverageProcessTimePerPacket() const { return _totalPackets == 0 ? 0 : _totalProcessTime / _totalPackets; } + quint64 getAverageLockWaitTimePerPacket() const { return _totalPackets == 0 ? 0 : _totalLockWaitTime / _totalPackets; } + quint64 getTotalElementsProcessed() const { return _totalElementsInPacket; } + quint64 getTotalPacketsProcessed() const { return _totalPackets; } + quint64 getAverageProcessTimePerElement() const { return _totalElementsInPacket == 0 ? 0 : _totalProcessTime / _totalElementsInPacket; } - uint64_t getAverageLockWaitTimePerElement() const + quint64 getAverageLockWaitTimePerElement() const { return _totalElementsInPacket == 0 ? 0 : _totalLockWaitTime / _totalElementsInPacket; } - uint64_t _totalTransitTime; - uint64_t _totalProcessTime; - uint64_t _totalLockWaitTime; - uint64_t _totalElementsInPacket; - uint64_t _totalPackets; + quint64 _totalTransitTime; + quint64 _totalProcessTime; + quint64 _totalLockWaitTime; + quint64 _totalElementsInPacket; + quint64 _totalPackets; }; typedef std::map NodeToSenderStatsMap; @@ -48,14 +48,14 @@ class OctreeInboundPacketProcessor : public ReceivedPacketProcessor { public: OctreeInboundPacketProcessor(OctreeServer* myServer); - uint64_t getAverageTransitTimePerPacket() const { return _totalPackets == 0 ? 0 : _totalTransitTime / _totalPackets; } - uint64_t getAverageProcessTimePerPacket() const { return _totalPackets == 0 ? 0 : _totalProcessTime / _totalPackets; } - uint64_t getAverageLockWaitTimePerPacket() const { return _totalPackets == 0 ? 0 : _totalLockWaitTime / _totalPackets; } - uint64_t getTotalElementsProcessed() const { return _totalElementsInPacket; } - uint64_t getTotalPacketsProcessed() const { return _totalPackets; } - uint64_t getAverageProcessTimePerElement() const + quint64 getAverageTransitTimePerPacket() const { return _totalPackets == 0 ? 0 : _totalTransitTime / _totalPackets; } + quint64 getAverageProcessTimePerPacket() const { return _totalPackets == 0 ? 0 : _totalProcessTime / _totalPackets; } + quint64 getAverageLockWaitTimePerPacket() const { return _totalPackets == 0 ? 0 : _totalLockWaitTime / _totalPackets; } + quint64 getTotalElementsProcessed() const { return _totalElementsInPacket; } + quint64 getTotalPacketsProcessed() const { return _totalPackets; } + quint64 getAverageProcessTimePerElement() const { return _totalElementsInPacket == 0 ? 0 : _totalProcessTime / _totalElementsInPacket; } - uint64_t getAverageLockWaitTimePerElement() const + quint64 getAverageLockWaitTimePerElement() const { return _totalElementsInPacket == 0 ? 0 : _totalLockWaitTime / _totalElementsInPacket; } void resetStats(); @@ -66,17 +66,17 @@ protected: virtual void processPacket(const HifiSockAddr& senderSockAddr, const QByteArray& packet); private: - void trackInboundPackets(const QUuid& nodeUUID, int sequence, uint64_t transitTime, - int voxelsInPacket, uint64_t processTime, uint64_t lockWaitTime); + void trackInboundPackets(const QUuid& nodeUUID, int sequence, quint64 transitTime, + int voxelsInPacket, quint64 processTime, quint64 lockWaitTime); OctreeServer* _myServer; int _receivedPacketCount; - uint64_t _totalTransitTime; - uint64_t _totalProcessTime; - uint64_t _totalLockWaitTime; - uint64_t _totalElementsInPacket; - uint64_t _totalPackets; + quint64 _totalTransitTime; + quint64 _totalProcessTime; + quint64 _totalLockWaitTime; + quint64 _totalElementsInPacket; + quint64 _totalPackets; NodeToSenderStatsMap _singleSenderStats; }; diff --git a/libraries/octree-server/src/OctreeQueryNode.cpp b/libraries/octree-server/src/OctreeQueryNode.cpp index e454658f07..f9363d9d80 100644 --- a/libraries/octree-server/src/OctreeQueryNode.cpp +++ b/libraries/octree-server/src/OctreeQueryNode.cpp @@ -69,7 +69,7 @@ bool OctreeQueryNode::shouldSuppressDuplicatePacket() { // How long has it been since we've sent one, if we're still under our max time, then keep considering // this packet for suppression - uint64_t now = usecTimestampNow(); + quint64 now = usecTimestampNow(); long sinceFirstSuppressedPacket = now - _firstSuppressedPacket; const long MAX_TIME_BETWEEN_DUPLICATE_PACKETS = 1000 * 1000; // 1 second. @@ -233,7 +233,7 @@ void OctreeQueryNode::updateLastKnownViewFrustum() { } // save that we know the view has been sent. - uint64_t now = usecTimestampNow(); + quint64 now = usecTimestampNow(); setLastTimeBagEmpty(now); // is this what we want? poor names } diff --git a/libraries/octree-server/src/OctreeQueryNode.h b/libraries/octree-server/src/OctreeQueryNode.h index c151bb0697..6d4dee300a 100644 --- a/libraries/octree-server/src/OctreeQueryNode.h +++ b/libraries/octree-server/src/OctreeQueryNode.h @@ -67,8 +67,8 @@ public: bool moveShouldDump() const; - uint64_t getLastTimeBagEmpty() const { return _lastTimeBagEmpty; } - void setLastTimeBagEmpty(uint64_t lastTimeBagEmpty) { _lastTimeBagEmpty = lastTimeBagEmpty; } + quint64 getLastTimeBagEmpty() const { return _lastTimeBagEmpty; } + void setLastTimeBagEmpty(quint64 lastTimeBagEmpty) { _lastTimeBagEmpty = lastTimeBagEmpty; } bool getCurrentPacketIsColor() const { return _currentPacketIsColor; } bool getCurrentPacketIsCompressed() const { return _currentPacketIsCompressed; } @@ -98,13 +98,13 @@ private: unsigned char* _lastOctreePacket; int _lastOctreePacketLength; int _duplicatePacketCount; - uint64_t _firstSuppressedPacket; + quint64 _firstSuppressedPacket; int _maxSearchLevel; int _maxLevelReachedInLastSearch; ViewFrustum _currentViewFrustum; ViewFrustum _lastKnownViewFrustum; - uint64_t _lastTimeBagEmpty; + quint64 _lastTimeBagEmpty; bool _viewFrustumChanging; bool _viewFrustumJustStoppedChanging; bool _currentPacketIsColor; diff --git a/libraries/octree-server/src/OctreeSendThread.cpp b/libraries/octree-server/src/OctreeSendThread.cpp index 7c63d4b0cd..26df0ffb0b 100644 --- a/libraries/octree-server/src/OctreeSendThread.cpp +++ b/libraries/octree-server/src/OctreeSendThread.cpp @@ -14,8 +14,8 @@ #include "OctreeServer.h" #include "OctreeServerConsts.h" -uint64_t startSceneSleepTime = 0; -uint64_t endSceneSleepTime = 0; +quint64 startSceneSleepTime = 0; +quint64 endSceneSleepTime = 0; OctreeSendThread::OctreeSendThread(const QUuid& nodeUUID, OctreeServer* myServer) : _nodeUUID(nodeUUID), @@ -25,7 +25,7 @@ OctreeSendThread::OctreeSendThread(const QUuid& nodeUUID, OctreeServer* myServer } bool OctreeSendThread::process() { - uint64_t start = usecTimestampNow(); + quint64 start = usecTimestampNow(); bool gotLock = false; // don't do any send processing until the initial load of the octree is complete... @@ -79,16 +79,16 @@ bool OctreeSendThread::process() { return isStillRunning(); // keep running till they terminate us } -uint64_t OctreeSendThread::_usleepTime = 0; -uint64_t OctreeSendThread::_usleepCalls = 0; +quint64 OctreeSendThread::_usleepTime = 0; +quint64 OctreeSendThread::_usleepCalls = 0; -uint64_t OctreeSendThread::_totalBytes = 0; -uint64_t OctreeSendThread::_totalWastedBytes = 0; -uint64_t OctreeSendThread::_totalPackets = 0; +quint64 OctreeSendThread::_totalBytes = 0; +quint64 OctreeSendThread::_totalWastedBytes = 0; +quint64 OctreeSendThread::_totalPackets = 0; int OctreeSendThread::handlePacketSend(Node* node, OctreeQueryNode* nodeData, int& trueBytesSent, int& truePacketsSent) { bool debug = _myServer->wantsDebugSending(); - uint64_t now = usecTimestampNow(); + quint64 now = usecTimestampNow(); bool packetSent = false; // did we send a packet? int packetsSent = 0; @@ -283,7 +283,7 @@ int OctreeSendThread::packetDistributor(Node* node, OctreeQueryNode* nodeData, b // If the current view frustum has changed OR we have nothing to send, then search against // the current view frustum for things to send. if (viewFrustumChanged || nodeData->nodeBag.isEmpty()) { - uint64_t now = usecTimestampNow(); + quint64 now = usecTimestampNow(); if (forceDebugging || (_myServer->wantsDebugSending() && _myServer->wantsVerboseDebug())) { qDebug("(viewFrustumChanged=%s || nodeData->nodeBag.isEmpty() =%s)...", debug::valueOf(viewFrustumChanged), debug::valueOf(nodeData->nodeBag.isEmpty())); @@ -310,7 +310,7 @@ int OctreeSendThread::packetDistributor(Node* node, OctreeQueryNode* nodeData, b if (!viewFrustumChanged && !nodeData->getWantDelta()) { // only set our last sent time if we weren't resetting due to frustum change - uint64_t now = usecTimestampNow(); + quint64 now = usecTimestampNow(); nodeData->setLastTimeBagEmpty(now); } @@ -374,9 +374,9 @@ int OctreeSendThread::packetDistributor(Node* node, OctreeQueryNode* nodeData, b // If we have something in our nodeBag, then turn them into packets and send them out... if (!nodeData->nodeBag.isEmpty()) { int bytesWritten = 0; - uint64_t start = usecTimestampNow(); - uint64_t startCompressTimeMsecs = OctreePacketData::getCompressContentTime() / 1000; - uint64_t startCompressCalls = OctreePacketData::getCompressContentCalls(); + quint64 start = usecTimestampNow(); + quint64 startCompressTimeMsecs = OctreePacketData::getCompressContentTime() / 1000; + quint64 startCompressCalls = OctreePacketData::getCompressContentCalls(); int clientMaxPacketsPerInterval = std::max(1,(nodeData->getMaxOctreePacketsPerSecond() / INTERVALS_PER_SECOND)); int maxPacketsPerInterval = std::min(clientMaxPacketsPerInterval, _myServer->getPacketsPerClientPerInterval()); @@ -533,13 +533,13 @@ int OctreeSendThread::packetDistributor(Node* node, OctreeQueryNode* nodeData, b } - uint64_t end = usecTimestampNow(); + quint64 end = usecTimestampNow(); int elapsedmsec = (end - start)/1000; - uint64_t endCompressCalls = OctreePacketData::getCompressContentCalls(); + quint64 endCompressCalls = OctreePacketData::getCompressContentCalls(); int elapsedCompressCalls = endCompressCalls - startCompressCalls; - uint64_t endCompressTimeMsecs = OctreePacketData::getCompressContentTime() / 1000; + quint64 endCompressTimeMsecs = OctreePacketData::getCompressContentTime() / 1000; int elapsedCompressTimeMsecs = endCompressTimeMsecs - startCompressTimeMsecs; diff --git a/libraries/octree-server/src/OctreeSendThread.h b/libraries/octree-server/src/OctreeSendThread.h index c0936371f2..6f60f0eb41 100644 --- a/libraries/octree-server/src/OctreeSendThread.h +++ b/libraries/octree-server/src/OctreeSendThread.h @@ -21,12 +21,12 @@ class OctreeSendThread : public GenericThread { public: OctreeSendThread(const QUuid& nodeUUID, OctreeServer* myServer); - static uint64_t _totalBytes; - static uint64_t _totalWastedBytes; - static uint64_t _totalPackets; + static quint64 _totalBytes; + static quint64 _totalWastedBytes; + static quint64 _totalPackets; - static uint64_t _usleepTime; - static uint64_t _usleepCalls; + static quint64 _usleepTime; + static quint64 _usleepCalls; protected: /// Implements generic processing behavior for this thread. diff --git a/libraries/octree-server/src/OctreeServer.cpp b/libraries/octree-server/src/OctreeServer.cpp index 9a3ce9aebc..9a4b0a51b3 100644 --- a/libraries/octree-server/src/OctreeServer.cpp +++ b/libraries/octree-server/src/OctreeServer.cpp @@ -120,7 +120,7 @@ bool OctreeServer::handleHTTPRequest(HTTPConnection* connection, const QString& } if (showStats) { - uint64_t checkSum; + quint64 checkSum; // return a 200 QString statsString("\r\n
\r\n");
         statsString += QString("Your %1 Server is running... [RELOAD]\r\n").arg(getMyServerName());
@@ -140,9 +140,9 @@ bool OctreeServer::handleHTTPRequest(HTTPConnection* connection, const QString&
 
         statsString += "\r\n";
 
-        uint64_t now  = usecTimestampNow();
+        quint64 now  = usecTimestampNow();
         const int USECS_PER_MSEC = 1000;
-        uint64_t msecsElapsed = (now - _startedUSecs) / USECS_PER_MSEC;
+        quint64 msecsElapsed = (now - _startedUSecs) / USECS_PER_MSEC;
         const int MSECS_PER_SEC = 1000;
         const int SECS_PER_MIN = 60;
         const int MIN_PER_HOUR = 60;
@@ -175,7 +175,7 @@ bool OctreeServer::handleHTTPRequest(HTTPConnection* connection, const QString&
 
             statsString += "\r\n";
 
-            uint64_t msecsElapsed = getLoadElapsedTime() / USECS_PER_MSEC;;
+            quint64 msecsElapsed = getLoadElapsedTime() / USECS_PER_MSEC;;
             float seconds = (msecsElapsed % MSECS_PER_MIN)/(float)MSECS_PER_SEC;
             int minutes = (msecsElapsed/(MSECS_PER_MIN)) % MIN_PER_HOUR;
             int hours = (msecsElapsed/(MSECS_PER_MIN * MIN_PER_HOUR));
@@ -226,12 +226,12 @@ bool OctreeServer::handleHTTPRequest(HTTPConnection* connection, const QString&
 
         // display outbound packet stats
         statsString += QString("%1 Outbound Packet Statistics...\r\n").arg(getMyServerName());
-        uint64_t totalOutboundPackets = OctreeSendThread::_totalPackets;
-        uint64_t totalOutboundBytes = OctreeSendThread::_totalBytes;
-        uint64_t totalWastedBytes = OctreeSendThread::_totalWastedBytes;
-        uint64_t totalBytesOfOctalCodes = OctreePacketData::getTotalBytesOfOctalCodes();
-        uint64_t totalBytesOfBitMasks = OctreePacketData::getTotalBytesOfBitMasks();
-        uint64_t totalBytesOfColor = OctreePacketData::getTotalBytesOfColor();
+        quint64 totalOutboundPackets = OctreeSendThread::_totalPackets;
+        quint64 totalOutboundBytes = OctreeSendThread::_totalBytes;
+        quint64 totalWastedBytes = OctreeSendThread::_totalWastedBytes;
+        quint64 totalBytesOfOctalCodes = OctreePacketData::getTotalBytesOfOctalCodes();
+        quint64 totalBytesOfBitMasks = OctreePacketData::getTotalBytesOfBitMasks();
+        quint64 totalBytesOfColor = OctreePacketData::getTotalBytesOfColor();
 
         const int COLUMN_WIDTH = 10;
         statsString += QString("           Total Outbound Packets: %1 packets\r\n")
@@ -256,13 +256,13 @@ bool OctreeServer::handleHTTPRequest(HTTPConnection* connection, const QString&
         // display inbound packet stats
         statsString += QString().sprintf("%s Edit Statistics... [RESET]\r\n",
                                          getMyServerName());
-        uint64_t averageTransitTimePerPacket = _octreeInboundPacketProcessor->getAverageTransitTimePerPacket();
-        uint64_t averageProcessTimePerPacket = _octreeInboundPacketProcessor->getAverageProcessTimePerPacket();
-        uint64_t averageLockWaitTimePerPacket = _octreeInboundPacketProcessor->getAverageLockWaitTimePerPacket();
-        uint64_t averageProcessTimePerElement = _octreeInboundPacketProcessor->getAverageProcessTimePerElement();
-        uint64_t averageLockWaitTimePerElement = _octreeInboundPacketProcessor->getAverageLockWaitTimePerElement();
-        uint64_t totalElementsProcessed = _octreeInboundPacketProcessor->getTotalElementsProcessed();
-        uint64_t totalPacketsProcessed = _octreeInboundPacketProcessor->getTotalPacketsProcessed();
+        quint64 averageTransitTimePerPacket = _octreeInboundPacketProcessor->getAverageTransitTimePerPacket();
+        quint64 averageProcessTimePerPacket = _octreeInboundPacketProcessor->getAverageProcessTimePerPacket();
+        quint64 averageLockWaitTimePerPacket = _octreeInboundPacketProcessor->getAverageLockWaitTimePerPacket();
+        quint64 averageProcessTimePerElement = _octreeInboundPacketProcessor->getAverageProcessTimePerElement();
+        quint64 averageLockWaitTimePerElement = _octreeInboundPacketProcessor->getAverageLockWaitTimePerElement();
+        quint64 totalElementsProcessed = _octreeInboundPacketProcessor->getTotalElementsProcessed();
+        quint64 totalPacketsProcessed = _octreeInboundPacketProcessor->getTotalPacketsProcessed();
 
         float averageElementsPerPacket = totalPacketsProcessed == 0 ? 0 : totalElementsProcessed / totalPacketsProcessed;
 
diff --git a/libraries/octree-server/src/OctreeServer.h b/libraries/octree-server/src/OctreeServer.h
index b17beb4a7e..48a74a5e9e 100644
--- a/libraries/octree-server/src/OctreeServer.h
+++ b/libraries/octree-server/src/OctreeServer.h
@@ -45,7 +45,7 @@ public:
 
     bool isInitialLoadComplete() const { return (_persistThread) ? _persistThread->isInitialLoadComplete() : true; }
     bool isPersistEnabled() const { return (_persistThread) ? true : false; }
-    uint64_t getLoadElapsedTime() const { return (_persistThread) ? _persistThread->getLoadElapsedTime() : 0; }
+    quint64 getLoadElapsedTime() const { return (_persistThread) ? _persistThread->getLoadElapsedTime() : 0; }
 
     // Subclasses must implement these methods
     virtual OctreeQueryNode* createOctreeQueryNode() = 0;
@@ -94,7 +94,7 @@ protected:
     static OctreeServer* _instance;
 
     time_t _started;
-    uint64_t _startedUSecs;
+    quint64 _startedUSecs;
 };
 
 #endif // __octree_server__OctreeServer__
diff --git a/libraries/octree/src/Octree.cpp b/libraries/octree/src/Octree.cpp
index d204d6487c..5e80fc83ff 100644
--- a/libraries/octree/src/Octree.cpp
+++ b/libraries/octree/src/Octree.cpp
@@ -445,7 +445,7 @@ void Octree::processRemoveOctreeElementsBitstream(const unsigned char* bitstream
 
     int numBytesPacketHeader = numBytesForPacketHeader(reinterpret_cast(bitstream));
     unsigned short int sequence = (*((unsigned short int*)(bitstream + numBytesPacketHeader)));
-    uint64_t sentAt = (*((uint64_t*)(bitstream + numBytesPacketHeader + sizeof(sequence))));
+    quint64 sentAt = (*((quint64*)(bitstream + numBytesPacketHeader + sizeof(sequence))));
 
     int atByte = numBytesPacketHeader + sizeof(sequence) + sizeof(sentAt);
 
diff --git a/libraries/octree/src/Octree.h b/libraries/octree/src/Octree.h
index 8ca7dec0e6..43a695f2ce 100644
--- a/libraries/octree/src/Octree.h
+++ b/libraries/octree/src/Octree.h
@@ -47,7 +47,7 @@ const bool WANT_OCCLUSION_CULLING = true;
 const int DONT_CHOP              = 0;
 const int NO_BOUNDARY_ADJUST     = 0;
 const int LOW_RES_MOVING_ADJUST  = 1;
-const uint64_t IGNORE_LAST_SENT  = 0;
+const quint64 IGNORE_LAST_SENT  = 0;
 
 #define IGNORE_SCENE_STATS       NULL
 #define IGNORE_VIEW_FRUSTUM      NULL
@@ -67,7 +67,7 @@ public:
     bool wantOcclusionCulling;
     int boundaryLevelAdjust;
     float octreeElementSizeScale;
-    uint64_t lastViewFrustumSent;
+    quint64 lastViewFrustumSent;
     bool forceSendScene;
     OctreeSceneStats* stats;
     CoverageMap* map;
@@ -100,7 +100,7 @@ public:
         CoverageMap* map = IGNORE_COVERAGE_MAP,
         int boundaryLevelAdjust = NO_BOUNDARY_ADJUST,
         float octreeElementSizeScale = DEFAULT_OCTREE_SIZE_SCALE,
-        uint64_t lastViewFrustumSent = IGNORE_LAST_SENT,
+        quint64 lastViewFrustumSent = IGNORE_LAST_SENT,
         bool forceSendScene = true,
         OctreeSceneStats* stats = IGNORE_SCENE_STATS,
         JurisdictionMap* jurisdictionMap = IGNORE_JURISDICTION_MAP) :
diff --git a/libraries/octree/src/OctreeConstants.h b/libraries/octree/src/OctreeConstants.h
index 31820b6fbc..a78d778f70 100644
--- a/libraries/octree/src/OctreeConstants.h
+++ b/libraries/octree/src/OctreeConstants.h
@@ -24,7 +24,7 @@ const glm::vec3 IDENTITY_RIGHT = glm::vec3( 1.0f, 0.0f, 0.0f);
 const glm::vec3 IDENTITY_UP    = glm::vec3( 0.0f, 1.0f, 0.0f);
 const glm::vec3 IDENTITY_FRONT = glm::vec3( 0.0f, 0.0f,-1.0f);
 
-const uint64_t CHANGE_FUDGE = 1000 * 200; // useconds of fudge in determining if we want to resend changed voxels
+const quint64 CHANGE_FUDGE = 1000 * 200; // useconds of fudge in determining if we want to resend changed voxels
 
 const int   TREE_SCALE = 16384; // ~10 miles.. This is the number of meters of the 0.0 to 1.0 voxel universe
 
diff --git a/libraries/octree/src/OctreeEditPacketSender.cpp b/libraries/octree/src/OctreeEditPacketSender.cpp
index b8f38e3b0b..5b84b819cc 100644
--- a/libraries/octree/src/OctreeEditPacketSender.cpp
+++ b/libraries/octree/src/OctreeEditPacketSender.cpp
@@ -100,9 +100,9 @@ void OctreeEditPacketSender::queuePacketToNode(const QUuid& nodeUUID, unsigned c
                 if (wantDebugging) {
                     int numBytesPacketHeader = numBytesForPacketHeader(reinterpret_cast(buffer));
                     unsigned short int sequence = (*((unsigned short int*)(buffer + numBytesPacketHeader)));
-                    uint64_t createdAt = (*((uint64_t*)(buffer + numBytesPacketHeader + sizeof(sequence))));
-                    uint64_t queuedAt = usecTimestampNow();
-                    uint64_t transitTime = queuedAt - createdAt;
+                    quint64 createdAt = (*((quint64*)(buffer + numBytesPacketHeader + sizeof(sequence))));
+                    quint64 queuedAt = usecTimestampNow();
+                    quint64 transitTime = queuedAt - createdAt;
 
                     qDebug() << "OctreeEditPacketSender::queuePacketToNode() queued " << buffer[0] <<
                             " - command to node bytes=" << length <<
@@ -163,7 +163,7 @@ void OctreeEditPacketSender::queuePacketToNodes(unsigned char* buffer, ssize_t l
 
     assert(serversExist()); // we must have jurisdictions to be here!!
 
-    int headerBytes = numBytesForPacketHeader(reinterpret_cast(buffer)) + sizeof(short) + sizeof(uint64_t);
+    int headerBytes = numBytesForPacketHeader(reinterpret_cast(buffer)) + sizeof(short) + sizeof(quint64);
     unsigned char* octCode = buffer + headerBytes; // skip the packet header to get to the octcode
 
     // We want to filter out edit messages for servers based on the server's Jurisdiction
@@ -307,10 +307,10 @@ void OctreeEditPacketSender::initializePacket(EditPacketBuffer& packetBuffer, Pa
     _sequenceNumber++;
 
     // pack in timestamp
-    uint64_t now = usecTimestampNow();
-    uint64_t* timeAt = (uint64_t*)&packetBuffer._currentBuffer[packetBuffer._currentSize];
+    quint64 now = usecTimestampNow();
+    quint64* timeAt = (quint64*)&packetBuffer._currentBuffer[packetBuffer._currentSize];
     *timeAt = now;
-    packetBuffer._currentSize += sizeof(uint64_t); // nudge past timestamp
+    packetBuffer._currentSize += sizeof(quint64); // nudge past timestamp
 
     packetBuffer._currentType = type;
 }
diff --git a/libraries/octree/src/OctreeElement.cpp b/libraries/octree/src/OctreeElement.cpp
index fbb2d9c08a..c536ad3eeb 100644
--- a/libraries/octree/src/OctreeElement.cpp
+++ b/libraries/octree/src/OctreeElement.cpp
@@ -23,11 +23,11 @@
 #include "OctreeElement.h"
 #include "Octree.h"
 
-uint64_t OctreeElement::_voxelMemoryUsage = 0;
-uint64_t OctreeElement::_octcodeMemoryUsage = 0;
-uint64_t OctreeElement::_externalChildrenMemoryUsage = 0;
-uint64_t OctreeElement::_voxelNodeCount = 0;
-uint64_t OctreeElement::_voxelNodeLeafCount = 0;
+quint64 OctreeElement::_voxelMemoryUsage = 0;
+quint64 OctreeElement::_octcodeMemoryUsage = 0;
+quint64 OctreeElement::_externalChildrenMemoryUsage = 0;
+quint64 OctreeElement::_voxelNodeCount = 0;
+quint64 OctreeElement::_voxelNodeLeafCount = 0;
 
 OctreeElement::OctreeElement() {
     // Note: you must call init() from your subclass, otherwise the OctreeElement will not be properly
@@ -270,23 +270,23 @@ void OctreeElement::auditChildren(const char* label) const {
 #endif // def HAS_AUDIT_CHILDREN
 
 
-uint64_t OctreeElement::_getChildAtIndexTime = 0;
-uint64_t OctreeElement::_getChildAtIndexCalls = 0;
-uint64_t OctreeElement::_setChildAtIndexTime = 0;
-uint64_t OctreeElement::_setChildAtIndexCalls = 0;
+quint64 OctreeElement::_getChildAtIndexTime = 0;
+quint64 OctreeElement::_getChildAtIndexCalls = 0;
+quint64 OctreeElement::_setChildAtIndexTime = 0;
+quint64 OctreeElement::_setChildAtIndexCalls = 0;
 
 #ifdef BLENDED_UNION_CHILDREN
-uint64_t OctreeElement::_singleChildrenCount = 0;
-uint64_t OctreeElement::_twoChildrenOffsetCount = 0;
-uint64_t OctreeElement::_twoChildrenExternalCount = 0;
-uint64_t OctreeElement::_threeChildrenOffsetCount = 0;
-uint64_t OctreeElement::_threeChildrenExternalCount = 0;
-uint64_t OctreeElement::_couldStoreFourChildrenInternally = 0;
-uint64_t OctreeElement::_couldNotStoreFourChildrenInternally = 0;
+quint64 OctreeElement::_singleChildrenCount = 0;
+quint64 OctreeElement::_twoChildrenOffsetCount = 0;
+quint64 OctreeElement::_twoChildrenExternalCount = 0;
+quint64 OctreeElement::_threeChildrenOffsetCount = 0;
+quint64 OctreeElement::_threeChildrenExternalCount = 0;
+quint64 OctreeElement::_couldStoreFourChildrenInternally = 0;
+quint64 OctreeElement::_couldNotStoreFourChildrenInternally = 0;
 #endif
 
-uint64_t OctreeElement::_externalChildrenCount = 0;
-uint64_t OctreeElement::_childrenCount[NUMBER_OF_CHILDREN + 1] = { 0, 0, 0, 0, 0, 0, 0, 0, 0 };
+quint64 OctreeElement::_externalChildrenCount = 0;
+quint64 OctreeElement::_childrenCount[NUMBER_OF_CHILDREN + 1] = { 0, 0, 0, 0, 0, 0, 0, 0, 0 };
 
 OctreeElement* OctreeElement::getChildAtIndex(int childIndex) const {
 #ifdef SIMPLE_CHILD_ARRAY
@@ -494,17 +494,17 @@ void OctreeElement::retrieveTwoChildren(OctreeElement*& childOne, OctreeElement*
 }
 
 void OctreeElement::decodeThreeOffsets(int64_t& offsetOne, int64_t& offsetTwo, int64_t& offsetThree) const {
-    const uint64_t ENCODE_BITS = 21;
-    const uint64_t ENCODE_MASK = 0xFFFFF;
-    const uint64_t ENCODE_MASK_SIGN = 0x100000;
+    const quint64 ENCODE_BITS = 21;
+    const quint64 ENCODE_MASK = 0xFFFFF;
+    const quint64 ENCODE_MASK_SIGN = 0x100000;
 
-    uint64_t offsetEncodedOne = (_children.offsetsThreeChildrenEncoded >> (ENCODE_BITS * 2)) & ENCODE_MASK;
-    uint64_t offsetEncodedTwo = (_children.offsetsThreeChildrenEncoded >> (ENCODE_BITS * 1)) & ENCODE_MASK;
-    uint64_t offsetEncodedThree = (_children.offsetsThreeChildrenEncoded & ENCODE_MASK);
+    quint64 offsetEncodedOne = (_children.offsetsThreeChildrenEncoded >> (ENCODE_BITS * 2)) & ENCODE_MASK;
+    quint64 offsetEncodedTwo = (_children.offsetsThreeChildrenEncoded >> (ENCODE_BITS * 1)) & ENCODE_MASK;
+    quint64 offsetEncodedThree = (_children.offsetsThreeChildrenEncoded & ENCODE_MASK);
 
-    uint64_t signEncodedOne = (_children.offsetsThreeChildrenEncoded >> (ENCODE_BITS * 2)) & ENCODE_MASK_SIGN;
-    uint64_t signEncodedTwo = (_children.offsetsThreeChildrenEncoded >> (ENCODE_BITS * 1)) & ENCODE_MASK_SIGN;
-    uint64_t signEncodedThree = (_children.offsetsThreeChildrenEncoded & ENCODE_MASK_SIGN);
+    quint64 signEncodedOne = (_children.offsetsThreeChildrenEncoded >> (ENCODE_BITS * 2)) & ENCODE_MASK_SIGN;
+    quint64 signEncodedTwo = (_children.offsetsThreeChildrenEncoded >> (ENCODE_BITS * 1)) & ENCODE_MASK_SIGN;
+    quint64 signEncodedThree = (_children.offsetsThreeChildrenEncoded & ENCODE_MASK_SIGN);
 
     bool oneNegative = signEncodedOne == ENCODE_MASK_SIGN;
     bool twoNegative = signEncodedTwo == ENCODE_MASK_SIGN;
@@ -516,11 +516,11 @@ void OctreeElement::decodeThreeOffsets(int64_t& offsetOne, int64_t& offsetTwo, i
 }
 
 void OctreeElement::encodeThreeOffsets(int64_t offsetOne, int64_t offsetTwo, int64_t offsetThree) {
-    const uint64_t ENCODE_BITS = 21;
-    const uint64_t ENCODE_MASK = 0xFFFFF;
-    const uint64_t ENCODE_MASK_SIGN = 0x100000;
+    const quint64 ENCODE_BITS = 21;
+    const quint64 ENCODE_MASK = 0xFFFFF;
+    const quint64 ENCODE_MASK_SIGN = 0x100000;
 
-    uint64_t offsetEncodedOne, offsetEncodedTwo, offsetEncodedThree;
+    quint64 offsetEncodedOne, offsetEncodedTwo, offsetEncodedThree;
     if (offsetOne < 0) {
         offsetEncodedOne = ((-offsetOne & ENCODE_MASK) | ENCODE_MASK_SIGN);
     } else {
diff --git a/libraries/octree/src/OctreeElement.h b/libraries/octree/src/OctreeElement.h
index 240bd10f98..38a30218d1 100644
--- a/libraries/octree/src/OctreeElement.h
+++ b/libraries/octree/src/OctreeElement.h
@@ -132,9 +132,9 @@ public:
     bool isDirty() const { return _isDirty; }
     void clearDirtyBit() { _isDirty = false; }
     void setDirtyBit() { _isDirty = true; }
-    bool hasChangedSince(uint64_t time) const { return (_lastChanged > time); }
+    bool hasChangedSince(quint64 time) const { return (_lastChanged > time); }
     void markWithChangedTime();
-    uint64_t getLastChanged() const { return _lastChanged; }
+    quint64 getLastChanged() const { return _lastChanged; }
     void handleSubtreeChanged(Octree* myTree);
     
     // Used by VoxelSystem for rendering in/out of view and LOD
@@ -158,28 +158,28 @@ public:
     static unsigned long getInternalNodeCount() { return _voxelNodeCount - _voxelNodeLeafCount; }
     static unsigned long getLeafNodeCount() { return _voxelNodeLeafCount; }
 
-    static uint64_t getVoxelMemoryUsage() { return _voxelMemoryUsage; }
-    static uint64_t getOctcodeMemoryUsage() { return _octcodeMemoryUsage; }
-    static uint64_t getExternalChildrenMemoryUsage() { return _externalChildrenMemoryUsage; }
-    static uint64_t getTotalMemoryUsage() { return _voxelMemoryUsage + _octcodeMemoryUsage + _externalChildrenMemoryUsage; }
+    static quint64 getVoxelMemoryUsage() { return _voxelMemoryUsage; }
+    static quint64 getOctcodeMemoryUsage() { return _octcodeMemoryUsage; }
+    static quint64 getExternalChildrenMemoryUsage() { return _externalChildrenMemoryUsage; }
+    static quint64 getTotalMemoryUsage() { return _voxelMemoryUsage + _octcodeMemoryUsage + _externalChildrenMemoryUsage; }
 
-    static uint64_t getGetChildAtIndexTime() { return _getChildAtIndexTime; }
-    static uint64_t getGetChildAtIndexCalls() { return _getChildAtIndexCalls; }
-    static uint64_t getSetChildAtIndexTime() { return _setChildAtIndexTime; }
-    static uint64_t getSetChildAtIndexCalls() { return _setChildAtIndexCalls; }
+    static quint64 getGetChildAtIndexTime() { return _getChildAtIndexTime; }
+    static quint64 getGetChildAtIndexCalls() { return _getChildAtIndexCalls; }
+    static quint64 getSetChildAtIndexTime() { return _setChildAtIndexTime; }
+    static quint64 getSetChildAtIndexCalls() { return _setChildAtIndexCalls; }
 
 #ifdef BLENDED_UNION_CHILDREN
-    static uint64_t getSingleChildrenCount() { return _singleChildrenCount; }
-    static uint64_t getTwoChildrenOffsetCount() { return _twoChildrenOffsetCount; }
-    static uint64_t getTwoChildrenExternalCount() { return _twoChildrenExternalCount; }
-    static uint64_t getThreeChildrenOffsetCount() { return _threeChildrenOffsetCount; }
-    static uint64_t getThreeChildrenExternalCount() { return _threeChildrenExternalCount; }
-    static uint64_t getCouldStoreFourChildrenInternally() { return _couldStoreFourChildrenInternally; }
-    static uint64_t getCouldNotStoreFourChildrenInternally() { return _couldNotStoreFourChildrenInternally; }
+    static quint64 getSingleChildrenCount() { return _singleChildrenCount; }
+    static quint64 getTwoChildrenOffsetCount() { return _twoChildrenOffsetCount; }
+    static quint64 getTwoChildrenExternalCount() { return _twoChildrenExternalCount; }
+    static quint64 getThreeChildrenOffsetCount() { return _threeChildrenOffsetCount; }
+    static quint64 getThreeChildrenExternalCount() { return _threeChildrenExternalCount; }
+    static quint64 getCouldStoreFourChildrenInternally() { return _couldStoreFourChildrenInternally; }
+    static quint64 getCouldNotStoreFourChildrenInternally() { return _couldNotStoreFourChildrenInternally; }
 #endif
 
-    static uint64_t getExternalChildrenCount() { return _externalChildrenCount; }
-    static uint64_t getChildrenCount(int childCount) { return _childrenCount[childCount]; }
+    static quint64 getExternalChildrenCount() { return _externalChildrenCount; }
+    static quint64 getChildrenCount(int childCount) { return _childrenCount[childCount]; }
     
 #ifdef BLENDED_UNION_CHILDREN
 #ifdef HAS_AUDIT_CHILDREN
@@ -227,7 +227,7 @@ protected:
       unsigned char* pointer;
     } _octalCode;  
 
-    uint64_t _lastChanged; /// Client and server, timestamp this node was last changed, 8 bytes
+    quint64 _lastChanged; /// Client and server, timestamp this node was last changed, 8 bytes
 
     /// Client and server, pointers to child nodes, various encodings
 #ifdef SIMPLE_CHILD_ARRAY
@@ -245,7 +245,7 @@ protected:
     union children_t {
       OctreeElement* single;
       int32_t offsetsTwoChildren[2];
-      uint64_t offsetsThreeChildrenEncoded;
+      quint64 offsetsThreeChildrenEncoded;
       OctreeElement** external;
     } _children;
 #ifdef HAS_AUDIT_CHILDREN
@@ -278,29 +278,29 @@ protected:
     //static QReadWriteLock _updateHooksLock;
     static std::vector _updateHooks;
 
-    static uint64_t _voxelNodeCount;
-    static uint64_t _voxelNodeLeafCount;
+    static quint64 _voxelNodeCount;
+    static quint64 _voxelNodeLeafCount;
 
-    static uint64_t _voxelMemoryUsage;
-    static uint64_t _octcodeMemoryUsage;
-    static uint64_t _externalChildrenMemoryUsage;
+    static quint64 _voxelMemoryUsage;
+    static quint64 _octcodeMemoryUsage;
+    static quint64 _externalChildrenMemoryUsage;
 
-    static uint64_t _getChildAtIndexTime;
-    static uint64_t _getChildAtIndexCalls;
-    static uint64_t _setChildAtIndexTime;
-    static uint64_t _setChildAtIndexCalls;
+    static quint64 _getChildAtIndexTime;
+    static quint64 _getChildAtIndexCalls;
+    static quint64 _setChildAtIndexTime;
+    static quint64 _setChildAtIndexCalls;
 
 #ifdef BLENDED_UNION_CHILDREN
-    static uint64_t _singleChildrenCount;
-    static uint64_t _twoChildrenOffsetCount;
-    static uint64_t _twoChildrenExternalCount;
-    static uint64_t _threeChildrenOffsetCount;
-    static uint64_t _threeChildrenExternalCount;
-    static uint64_t _couldStoreFourChildrenInternally;
-    static uint64_t _couldNotStoreFourChildrenInternally;
+    static quint64 _singleChildrenCount;
+    static quint64 _twoChildrenOffsetCount;
+    static quint64 _twoChildrenExternalCount;
+    static quint64 _threeChildrenOffsetCount;
+    static quint64 _threeChildrenExternalCount;
+    static quint64 _couldStoreFourChildrenInternally;
+    static quint64 _couldNotStoreFourChildrenInternally;
 #endif
-    static uint64_t _externalChildrenCount;
-    static uint64_t _childrenCount[NUMBER_OF_CHILDREN + 1];
+    static quint64 _externalChildrenCount;
+    static quint64 _childrenCount[NUMBER_OF_CHILDREN + 1];
 };
 
 #endif /* defined(__hifi__OctreeElement__) */
\ No newline at end of file
diff --git a/libraries/octree/src/OctreePacketData.cpp b/libraries/octree/src/OctreePacketData.cpp
index 9e7d88416b..44c302dc59 100644
--- a/libraries/octree/src/OctreePacketData.cpp
+++ b/libraries/octree/src/OctreePacketData.cpp
@@ -10,12 +10,12 @@
 #include "OctreePacketData.h"
 
 bool OctreePacketData::_debug = false;
-uint64_t OctreePacketData::_totalBytesOfOctalCodes = 0;
-uint64_t OctreePacketData::_totalBytesOfBitMasks = 0;
-uint64_t OctreePacketData::_totalBytesOfColor = 0;
-uint64_t OctreePacketData::_totalBytesOfValues = 0;
-uint64_t OctreePacketData::_totalBytesOfPositions = 0;
-uint64_t OctreePacketData::_totalBytesOfRawData = 0;
+quint64 OctreePacketData::_totalBytesOfOctalCodes = 0;
+quint64 OctreePacketData::_totalBytesOfBitMasks = 0;
+quint64 OctreePacketData::_totalBytesOfColor = 0;
+quint64 OctreePacketData::_totalBytesOfValues = 0;
+quint64 OctreePacketData::_totalBytesOfPositions = 0;
+quint64 OctreePacketData::_totalBytesOfRawData = 0;
 
 
 
@@ -272,7 +272,7 @@ bool OctreePacketData::appendValue(uint32_t value) {
     return success;
 }
 
-bool OctreePacketData::appendValue(uint64_t value) {
+bool OctreePacketData::appendValue(quint64 value) {
     const unsigned char* data = (const unsigned char*)&value;
     int length = sizeof(value);
     bool success = append(data, length);
@@ -334,8 +334,8 @@ bool OctreePacketData::appendRawData(const unsigned char* data, int length) {
     return success;
 }
 
-uint64_t OctreePacketData::_compressContentTime = 0;
-uint64_t OctreePacketData::_compressContentCalls = 0;
+quint64 OctreePacketData::_compressContentTime = 0;
+quint64 OctreePacketData::_compressContentCalls = 0;
 
 bool OctreePacketData::compressContent() { 
     PerformanceWarning warn(false, "OctreePacketData::compressContent()", false, &_compressContentTime, &_compressContentCalls);
diff --git a/libraries/octree/src/OctreePacketData.h b/libraries/octree/src/OctreePacketData.h
index 1a2b160c81..9ef7399fe0 100644
--- a/libraries/octree/src/OctreePacketData.h
+++ b/libraries/octree/src/OctreePacketData.h
@@ -25,7 +25,7 @@
 
 typedef unsigned char OCTREE_PACKET_FLAGS;
 typedef uint16_t OCTREE_PACKET_SEQUENCE;
-typedef uint64_t OCTREE_PACKET_SENT_TIME;
+typedef quint64 OCTREE_PACKET_SENT_TIME;
 typedef uint16_t OCTREE_PACKET_INTERNAL_SECTION_SIZE;
 const int MAX_OCTREE_PACKET_SIZE = MAX_PACKET_SIZE;
 
@@ -124,7 +124,7 @@ public:
     bool appendValue(uint32_t value);
 
     /// appends a unsigned 64 bit int to the end of the stream, may fail if new data stream is too long to fit in packet
-    bool appendValue(uint64_t value);
+    bool appendValue(quint64 value);
 
     /// appends a float value to the end of the stream, may fail if new data stream is too long to fit in packet
     bool appendValue(float value);
@@ -170,11 +170,11 @@ public:
     /// displays contents for debugging
     void debugContent();
     
-    static uint64_t getCompressContentTime() { return _compressContentTime; } /// total time spent compressing content
-    static uint64_t getCompressContentCalls() { return _compressContentCalls; } /// total calls to compress content
-    static uint64_t getTotalBytesOfOctalCodes() { return _totalBytesOfOctalCodes; }  /// total bytes for octal codes
-    static uint64_t getTotalBytesOfBitMasks() { return _totalBytesOfBitMasks; }  /// total bytes of bitmasks
-    static uint64_t getTotalBytesOfColor() { return _totalBytesOfColor; } /// total bytes of color
+    static quint64 getCompressContentTime() { return _compressContentTime; } /// total time spent compressing content
+    static quint64 getCompressContentCalls() { return _compressContentCalls; } /// total calls to compress content
+    static quint64 getTotalBytesOfOctalCodes() { return _totalBytesOfOctalCodes; }  /// total bytes for octal codes
+    static quint64 getTotalBytesOfBitMasks() { return _totalBytesOfBitMasks; }  /// total bytes of bitmasks
+    static quint64 getTotalBytesOfColor() { return _totalBytesOfColor; } /// total bytes of color
 
 private:
     /// appends raw bytes, might fail if byte would cause packet to be too large
@@ -210,15 +210,15 @@ private:
 
     static bool _debug;
 
-    static uint64_t _compressContentTime;
-    static uint64_t _compressContentCalls;
+    static quint64 _compressContentTime;
+    static quint64 _compressContentCalls;
 
-    static uint64_t _totalBytesOfOctalCodes;
-    static uint64_t _totalBytesOfBitMasks;
-    static uint64_t _totalBytesOfColor;
-    static uint64_t _totalBytesOfValues;
-    static uint64_t _totalBytesOfPositions;
-    static uint64_t _totalBytesOfRawData;
+    static quint64 _totalBytesOfOctalCodes;
+    static quint64 _totalBytesOfBitMasks;
+    static quint64 _totalBytesOfColor;
+    static quint64 _totalBytesOfValues;
+    static quint64 _totalBytesOfPositions;
+    static quint64 _totalBytesOfRawData;
 };
 
 #endif /* defined(__hifi__OctreePacketData__) */
\ No newline at end of file
diff --git a/libraries/octree/src/OctreePersistThread.cpp b/libraries/octree/src/OctreePersistThread.cpp
index 052773f475..c6c3ce2a6a 100644
--- a/libraries/octree/src/OctreePersistThread.cpp
+++ b/libraries/octree/src/OctreePersistThread.cpp
@@ -25,7 +25,7 @@ OctreePersistThread::OctreePersistThread(Octree* tree, const QString& filename,
 bool OctreePersistThread::process() {
 
     if (!_initialLoadComplete) {
-        uint64_t loadStarted = usecTimestampNow();
+        quint64 loadStarted = usecTimestampNow();
         qDebug() << "loading Octrees from file: " << _filename << "...";
 
         bool persistantFileRead;
@@ -37,7 +37,7 @@ bool OctreePersistThread::process() {
         }
         _tree->unlock();
 
-        uint64_t loadDone = usecTimestampNow();
+        quint64 loadDone = usecTimestampNow();
         _loadTimeUSecs = loadDone - loadStarted;
 
         _tree->clearDirtyBit(); // the tree is clean since we just loaded it
@@ -63,8 +63,8 @@ bool OctreePersistThread::process() {
     }
 
     if (isStillRunning()) {
-        uint64_t MSECS_TO_USECS = 1000;
-        uint64_t USECS_TO_SLEEP = 10 * MSECS_TO_USECS; // every 10ms
+        quint64 MSECS_TO_USECS = 1000;
+        quint64 USECS_TO_SLEEP = 10 * MSECS_TO_USECS; // every 10ms
         usleep(USECS_TO_SLEEP);
 
         // do our updates then check to save...
@@ -72,9 +72,9 @@ bool OctreePersistThread::process() {
         _tree->update();
         _tree->unlock();
 
-        uint64_t now = usecTimestampNow();
-        uint64_t sinceLastSave = now - _lastCheck;
-        uint64_t intervalToCheck = _persistInterval * MSECS_TO_USECS;
+        quint64 now = usecTimestampNow();
+        quint64 sinceLastSave = now - _lastCheck;
+        quint64 intervalToCheck = _persistInterval * MSECS_TO_USECS;
 
         if (sinceLastSave > intervalToCheck) {
             // check the dirty bit and persist here...
diff --git a/libraries/octree/src/OctreePersistThread.h b/libraries/octree/src/OctreePersistThread.h
index 9bdafe5225..ce6190b0e6 100644
--- a/libraries/octree/src/OctreePersistThread.h
+++ b/libraries/octree/src/OctreePersistThread.h
@@ -24,7 +24,7 @@ public:
     OctreePersistThread(Octree* tree, const QString& filename, int persistInterval = DEFAULT_PERSIST_INTERVAL);
 
     bool isInitialLoadComplete() const { return _initialLoadComplete; }
-    uint64_t getLoadElapsedTime() const { return _loadTimeUSecs; }
+    quint64 getLoadElapsedTime() const { return _loadTimeUSecs; }
 
 signals:
     void loadCompleted();
@@ -38,8 +38,8 @@ private:
     int _persistInterval;
     bool _initialLoadComplete;
 
-    uint64_t _loadTimeUSecs;
-    uint64_t _lastCheck;
+    quint64 _loadTimeUSecs;
+    quint64 _lastCheck;
 };
 
 #endif // __Octree_server__OctreePersistThread__
diff --git a/libraries/octree/src/OctreeQuery.h b/libraries/octree/src/OctreeQuery.h
index 98e27e48bd..acb4b7cb32 100644
--- a/libraries/octree/src/OctreeQuery.h
+++ b/libraries/octree/src/OctreeQuery.h
@@ -20,7 +20,7 @@ typedef unsigned char  uint8_t;
 typedef unsigned short uint16_t;
 typedef unsigned int   uint32_t;
 typedef signed long long   int64_t;
-typedef unsigned long long uint64_t;
+typedef unsigned long long quint64;
 #define PRId64 "I64d"
 #else
 #include 
diff --git a/libraries/octree/src/OctreeSceneStats.cpp b/libraries/octree/src/OctreeSceneStats.cpp
index 6a57fbf303..59287e3c5c 100644
--- a/libraries/octree/src/OctreeSceneStats.cpp
+++ b/libraries/octree/src/OctreeSceneStats.cpp
@@ -691,7 +691,7 @@ OctreeSceneStats::ItemInfo OctreeSceneStats::_ITEMS[] = {
 };
 
 const char* OctreeSceneStats::getItemValue(Item item) {
-    const uint64_t USECS_PER_SECOND = 1000 * 1000;
+    const quint64 USECS_PER_SECOND = 1000 * 1000;
     int calcFPS, calcAverageFPS, calculatedKBPS;
     switch(item) {
         case ITEM_ELAPSED: {
diff --git a/libraries/octree/src/OctreeSceneStats.h b/libraries/octree/src/OctreeSceneStats.h
index 350470b9c1..bf65e85ad4 100644
--- a/libraries/octree/src/OctreeSceneStats.h
+++ b/libraries/octree/src/OctreeSceneStats.h
@@ -172,17 +172,17 @@ private:
 
     // scene timing data in usecs
     bool _isStarted;
-    uint64_t _start;
-    uint64_t _end;
-    uint64_t _elapsed;
-    uint64_t _lastFullElapsed;
+    quint64 _start;
+    quint64 _end;
+    quint64 _elapsed;
+    quint64 _lastFullElapsed;
     
     SimpleMovingAverage _elapsedAverage;
     SimpleMovingAverage _bitsPerOctreeAverage;
 
-    uint64_t _totalEncodeTime;
-    uint64_t _lastFullTotalEncodeTime;
-    uint64_t _encodeStart;
+    quint64 _totalEncodeTime;
+    quint64 _lastFullTotalEncodeTime;
+    quint64 _encodeStart;
     
     // scene octree related data
     unsigned long _totalElements;
diff --git a/libraries/particle-server/src/ParticleNodeData.h b/libraries/particle-server/src/ParticleNodeData.h
index da5a9b0b71..4ab16cb33a 100644
--- a/libraries/particle-server/src/ParticleNodeData.h
+++ b/libraries/particle-server/src/ParticleNodeData.h
@@ -21,11 +21,11 @@ public:
 
     virtual PacketType getMyPacketType() const { return PacketTypeParticleData; }
 
-    uint64_t getLastDeletedParticlesSentAt() const { return _lastDeletedParticlesSentAt; }
-    void setLastDeletedParticlesSentAt(uint64_t sentAt) { _lastDeletedParticlesSentAt = sentAt; }
+    quint64 getLastDeletedParticlesSentAt() const { return _lastDeletedParticlesSentAt; }
+    void setLastDeletedParticlesSentAt(quint64 sentAt) { _lastDeletedParticlesSentAt = sentAt; }
 
 private:
-    uint64_t _lastDeletedParticlesSentAt;
+    quint64 _lastDeletedParticlesSentAt;
 };
 
 #endif /* defined(__hifi__ParticleNodeData__) */
diff --git a/libraries/particle-server/src/ParticleServer.cpp b/libraries/particle-server/src/ParticleServer.cpp
index 94bc3c3a16..9344d8c4ae 100644
--- a/libraries/particle-server/src/ParticleServer.cpp
+++ b/libraries/particle-server/src/ParticleServer.cpp
@@ -76,7 +76,7 @@ bool ParticleServer::hasSpecialPacketToSend(Node* node) {
     // check to see if any new particles have been added since we last sent to this node...
     ParticleNodeData* nodeData = static_cast(node->getLinkedData());
     if (nodeData) {
-        uint64_t deletedParticlesSentAt = nodeData->getLastDeletedParticlesSentAt();
+        quint64 deletedParticlesSentAt = nodeData->getLastDeletedParticlesSentAt();
 
         ParticleTree* tree = static_cast(_tree);
         shouldSendDeletedParticles = tree->hasParticlesDeletedSince(deletedParticlesSentAt);
@@ -91,8 +91,8 @@ int ParticleServer::sendSpecialPacket(Node* node) {
 
     ParticleNodeData* nodeData = static_cast(node->getLinkedData());
     if (nodeData) {
-        uint64_t deletedParticlesSentAt = nodeData->getLastDeletedParticlesSentAt();
-        uint64_t deletePacketSentAt = usecTimestampNow();
+        quint64 deletedParticlesSentAt = nodeData->getLastDeletedParticlesSentAt();
+        quint64 deletePacketSentAt = usecTimestampNow();
 
         ParticleTree* tree = static_cast(_tree);
         bool hasMoreToSend = true;
@@ -121,11 +121,11 @@ void ParticleServer::pruneDeletedParticles() {
     if (tree->hasAnyDeletedParticles()) {
 
         //qDebug() << "there are some deleted particles to consider...";
-        uint64_t earliestLastDeletedParticlesSent = usecTimestampNow() + 1; // in the future
+        quint64 earliestLastDeletedParticlesSent = usecTimestampNow() + 1; // in the future
         foreach (const SharedNodePointer& otherNode, NodeList::getInstance()->getNodeHash()) {
             if (otherNode->getLinkedData()) {
                 ParticleNodeData* nodeData = static_cast(otherNode->getLinkedData());
-                uint64_t nodeLastDeletedParticlesSentAt = nodeData->getLastDeletedParticlesSentAt();
+                quint64 nodeLastDeletedParticlesSentAt = nodeData->getLastDeletedParticlesSentAt();
                 if (nodeLastDeletedParticlesSentAt < earliestLastDeletedParticlesSent) {
                     earliestLastDeletedParticlesSent = nodeLastDeletedParticlesSentAt;
                 }
diff --git a/libraries/particles/src/Particle.cpp b/libraries/particles/src/Particle.cpp
index 340a560439..3ed551b506 100644
--- a/libraries/particles/src/Particle.cpp
+++ b/libraries/particles/src/Particle.cpp
@@ -89,7 +89,7 @@ void Particle::init(glm::vec3 position, float radius, rgbColor color, glm::vec3
         _id = id;
         //qDebug() << "Particle::init()... assigning id from init... _id=" << _id;
     }
-    uint64_t now = usecTimestampNow();
+    quint64 now = usecTimestampNow();
     _lastEdited = now;
     _lastUpdated = now;
     _created = now; // will get updated as appropriate in setAge()
@@ -169,8 +169,8 @@ bool Particle::appendParticleData(OctreePacketData* packetData) const {
 int Particle::expectedBytes() {
     int expectedBytes = sizeof(uint32_t) // id
                 + sizeof(float) // age
-                + sizeof(uint64_t) // last updated
-                + sizeof(uint64_t) // lasted edited
+                + sizeof(quint64) // last updated
+                + sizeof(quint64) // lasted edited
                 + sizeof(float) // radius
                 + sizeof(glm::vec3) // position
                 + sizeof(rgbColor) // color
@@ -185,7 +185,7 @@ int Particle::expectedBytes() {
 
 int Particle::expectedEditMessageBytes() {
     int expectedBytes = sizeof(uint32_t) // id
-                + sizeof(uint64_t) // lasted edited
+                + sizeof(quint64) // lasted edited
                 + sizeof(float) // radius
                 + sizeof(glm::vec3) // position
                 + sizeof(rgbColor) // color
@@ -514,7 +514,7 @@ bool Particle::encodeParticleEditMessageDetails(PacketType command, ParticleID i
         }
 
         // lastEdited
-        uint64_t lastEdited = properties.getLastEdited();
+        quint64 lastEdited = properties.getLastEdited();
         memcpy(copyAt, &lastEdited, sizeof(lastEdited));
         copyAt += sizeof(lastEdited);
         sizeOut += sizeof(lastEdited);
@@ -646,9 +646,9 @@ void Particle::adjustEditPacketForClockSkew(unsigned char* codeColorBuffer, ssiz
     }
 
     // lastEdited
-    uint64_t lastEditedInLocalTime;
+    quint64 lastEditedInLocalTime;
     memcpy(&lastEditedInLocalTime, dataAt, sizeof(lastEditedInLocalTime));
-    uint64_t lastEditedInServerTime = lastEditedInLocalTime + clockSkew;
+    quint64 lastEditedInServerTime = lastEditedInLocalTime + clockSkew;
     memcpy(dataAt, &lastEditedInServerTime, sizeof(lastEditedInServerTime));
     const bool wantDebug = false;
     if (wantDebug) {
@@ -663,14 +663,14 @@ void Particle::adjustEditPacketForClockSkew(unsigned char* codeColorBuffer, ssiz
 const float MIN_EXPECTED_FRAME_PERIOD = 0.005f;  // 1/200th of a second
 const float MIN_VALID_SPEED = 9.8 * MIN_EXPECTED_FRAME_PERIOD / (float)(TREE_SCALE);
 
-void Particle::update(const uint64_t& now) {
+void Particle::update(const quint64& now) {
     float timeElapsed = (float)(now - _lastUpdated) / (float)(USECS_PER_SECOND);
     _lastUpdated = now;
 
     // calculate our default shouldDie state... then allow script to change it if it wants...
     float speed = glm::length(_velocity);
     bool isStopped = (speed < MIN_VALID_SPEED);
-    const uint64_t REALLY_OLD = 30 * USECS_PER_SECOND; // 30 seconds
+    const quint64 REALLY_OLD = 30 * USECS_PER_SECOND; // 30 seconds
     bool isReallyOld = ((now - _created) > REALLY_OLD);
     bool isInHand = getInHand();
     bool shouldDie = (getAge() > getLifetime()) || getShouldDie() || (!isInHand && isStopped && isReallyOld);
@@ -799,7 +799,7 @@ void Particle::collisionWithVoxel(VoxelDetail* voxelDetails) {
 
 
 void Particle::setAge(float age) {
-    uint64_t ageInUsecs = age * USECS_PER_SECOND;
+    quint64 ageInUsecs = age * USECS_PER_SECOND;
     _created = usecTimestampNow() - ageInUsecs;
 }
 
diff --git a/libraries/particles/src/Particle.h b/libraries/particles/src/Particle.h
index 6046ca39de..5b30e4f031 100644
--- a/libraries/particles/src/Particle.h
+++ b/libraries/particles/src/Particle.h
@@ -76,7 +76,7 @@ public:
     bool getInHand() const { return _inHand; }
     bool getShouldDie() const { return _shouldDie; }
 
-    uint64_t getLastEdited() const { return _lastEdited; }
+    quint64 getLastEdited() const { return _lastEdited; }
     uint16_t getChangedBits() const;
 
     /// set position in meter units
@@ -112,7 +112,7 @@ private:
 
     uint32_t _id;
     bool _idSet;
-    uint64_t _lastEdited;
+    quint64 _lastEdited;
     bool _positionChanged;
     bool _colorChanged;
     bool _radiusChanged;
@@ -198,10 +198,10 @@ public:
     ParticleProperties getProperties() const;
 
     /// The last updated/simulated time of this particle from the time perspective of the authoritative server/source
-    uint64_t getLastUpdated() const { return _lastUpdated; }
+    quint64 getLastUpdated() const { return _lastUpdated; }
 
     /// The last edited time of this particle from the time perspective of the authoritative server/source
-    uint64_t getLastEdited() const { return _lastEdited; }
+    quint64 getLastEdited() const { return _lastEdited; }
 
     /// lifetime of the particle in seconds
     float getAge() const { return static_cast(usecTimestampNow() - _created) / static_cast(USECS_PER_SECOND); }
@@ -247,7 +247,7 @@ public:
 
     static void adjustEditPacketForClockSkew(unsigned char* codeColorBuffer, ssize_t length, int clockSkew);
 
-    void update(const uint64_t& now);
+    void update(const quint64& now);
     void collisionWithParticle(Particle* other);
     void collisionWithVoxel(VoxelDetail* voxel);
 
@@ -300,11 +300,11 @@ protected:
     uint32_t _creatorTokenID;
     bool _newlyCreated;
 
-    uint64_t _lastUpdated;
-    uint64_t _lastEdited;
+    quint64 _lastUpdated;
+    quint64 _lastEdited;
 
     // this doesn't go on the wire, we send it as lifetime
-    uint64_t _created;
+    quint64 _created;
 
     // used by the static interfaces for creator token ids
     static uint32_t _nextCreatorTokenID;
diff --git a/libraries/particles/src/ParticleTree.cpp b/libraries/particles/src/ParticleTree.cpp
index a23c393f44..933a29775f 100644
--- a/libraries/particles/src/ParticleTree.cpp
+++ b/libraries/particles/src/ParticleTree.cpp
@@ -336,7 +336,7 @@ void ParticleTree::update() {
             storeParticle(args._movingParticles[i]);
         } else {
             uint32_t particleID = args._movingParticles[i].getID();
-            uint64_t deletedAt = usecTimestampNow();
+            quint64 deletedAt = usecTimestampNow();
             _recentlyDeletedParticlesLock.lockForWrite();
             _recentlyDeletedParticleIDs.insert(deletedAt, particleID);
             _recentlyDeletedParticlesLock.unlock();
@@ -348,12 +348,12 @@ void ParticleTree::update() {
 }
 
 
-bool ParticleTree::hasParticlesDeletedSince(uint64_t sinceTime) {
+bool ParticleTree::hasParticlesDeletedSince(quint64 sinceTime) {
     // we can probably leverage the ordered nature of QMultiMap to do this quickly...
     bool hasSomethingNewer = false;
 
     _recentlyDeletedParticlesLock.lockForRead();
-    QMultiMap::const_iterator iterator = _recentlyDeletedParticleIDs.constBegin();
+    QMultiMap::const_iterator iterator = _recentlyDeletedParticleIDs.constBegin();
     while (iterator != _recentlyDeletedParticleIDs.constEnd()) {
         //qDebug() << "considering... time/key:" << iterator.key();
         if (iterator.key() > sinceTime) {
@@ -367,7 +367,7 @@ bool ParticleTree::hasParticlesDeletedSince(uint64_t sinceTime) {
 }
 
 // sinceTime is an in/out parameter - it will be side effected with the last time sent out
-bool ParticleTree::encodeParticlesDeletedSince(uint64_t& sinceTime, unsigned char* outputBuffer, size_t maxLength,
+bool ParticleTree::encodeParticlesDeletedSince(quint64& sinceTime, unsigned char* outputBuffer, size_t maxLength,
                                                     size_t& outputLength) {
 
     bool hasMoreToSend = true;
@@ -386,7 +386,7 @@ bool ParticleTree::encodeParticlesDeletedSince(uint64_t& sinceTime, unsigned cha
     // we keep a multi map of particle IDs to timestamps, we only want to include the particle IDs that have been
     // deleted since we last sent to this node
     _recentlyDeletedParticlesLock.lockForRead();
-    QMultiMap::const_iterator iterator = _recentlyDeletedParticleIDs.constBegin();
+    QMultiMap::const_iterator iterator = _recentlyDeletedParticleIDs.constBegin();
     while (iterator != _recentlyDeletedParticleIDs.constEnd()) {
         QList values = _recentlyDeletedParticleIDs.values(iterator.key());
         for (int valueItem = 0; valueItem < values.size(); ++valueItem) {
@@ -431,12 +431,12 @@ bool ParticleTree::encodeParticlesDeletedSince(uint64_t& sinceTime, unsigned cha
 }
 
 // called by the server when it knows all nodes have been sent deleted packets
-void ParticleTree::forgetParticlesDeletedBefore(uint64_t sinceTime) {
+void ParticleTree::forgetParticlesDeletedBefore(quint64 sinceTime) {
     //qDebug() << "forgetParticlesDeletedBefore()";
-    QSet keysToRemove;
+    QSet keysToRemove;
 
     _recentlyDeletedParticlesLock.lockForWrite();
-    QMultiMap::iterator iterator = _recentlyDeletedParticleIDs.begin();
+    QMultiMap::iterator iterator = _recentlyDeletedParticleIDs.begin();
     // First find all the keys in the map that are older and need to be deleted    
     while (iterator != _recentlyDeletedParticleIDs.end()) {
         //qDebug() << "considering... time/key:" << iterator.key();
@@ -448,7 +448,7 @@ void ParticleTree::forgetParticlesDeletedBefore(uint64_t sinceTime) {
     }
 
     // Now run through the keysToRemove and remove them    
-    foreach (uint64_t value, keysToRemove) {
+    foreach (quint64 value, keysToRemove) {
         //qDebug() << "removing the key, _recentlyDeletedParticleIDs.remove(value); time/key:" << value;
         _recentlyDeletedParticleIDs.remove(value);
     }
diff --git a/libraries/particles/src/ParticleTree.h b/libraries/particles/src/ParticleTree.h
index af15666ff7..12ac693f32 100644
--- a/libraries/particles/src/ParticleTree.h
+++ b/libraries/particles/src/ParticleTree.h
@@ -48,9 +48,9 @@ public:
     void removeNewlyCreatedHook(NewlyCreatedParticleHook* hook);
 
     bool hasAnyDeletedParticles() const { return _recentlyDeletedParticleIDs.size() > 0; }
-    bool hasParticlesDeletedSince(uint64_t sinceTime);
-    bool encodeParticlesDeletedSince(uint64_t& sinceTime, unsigned char* packetData, size_t maxLength, size_t& outputLength);
-    void forgetParticlesDeletedBefore(uint64_t sinceTime);
+    bool hasParticlesDeletedSince(quint64 sinceTime);
+    bool encodeParticlesDeletedSince(quint64& sinceTime, unsigned char* packetData, size_t maxLength, size_t& outputLength);
+    void forgetParticlesDeletedBefore(quint64 sinceTime);
 
     void processEraseMessage(const QByteArray& dataByteArray, const HifiSockAddr& senderSockAddr, Node* sourceNode);
 
@@ -71,7 +71,7 @@ private:
 
 
     QReadWriteLock _recentlyDeletedParticlesLock;
-    QMultiMap _recentlyDeletedParticleIDs;
+    QMultiMap _recentlyDeletedParticleIDs;
 };
 
 #endif /* defined(__hifi__ParticleTree__) */
diff --git a/libraries/shared/src/Node.h b/libraries/shared/src/Node.h
index 15dfd633b1..60d14a9dd3 100644
--- a/libraries/shared/src/Node.h
+++ b/libraries/shared/src/Node.h
@@ -55,11 +55,11 @@ public:
     const QUuid& getUUID() const { return _uuid; }
     void setUUID(const QUuid& uuid) { _uuid = uuid; }
 
-    uint64_t getWakeMicrostamp() const { return _wakeMicrostamp; }
-    void setWakeMicrostamp(uint64_t wakeMicrostamp) { _wakeMicrostamp = wakeMicrostamp; }
+    quint64 getWakeMicrostamp() const { return _wakeMicrostamp; }
+    void setWakeMicrostamp(quint64 wakeMicrostamp) { _wakeMicrostamp = wakeMicrostamp; }
 
-    uint64_t getLastHeardMicrostamp() const { return _lastHeardMicrostamp; }
-    void setLastHeardMicrostamp(uint64_t lastHeardMicrostamp) { _lastHeardMicrostamp = lastHeardMicrostamp; }
+    quint64 getLastHeardMicrostamp() const { return _lastHeardMicrostamp; }
+    void setLastHeardMicrostamp(quint64 lastHeardMicrostamp) { _lastHeardMicrostamp = lastHeardMicrostamp; }
 
     const HifiSockAddr& getPublicSocket() const { return _publicSocket; }
     void setPublicSocket(const HifiSockAddr& publicSocket);
@@ -98,8 +98,8 @@ private:
 
     NODE_TYPE _type;
     QUuid _uuid;
-    uint64_t _wakeMicrostamp;
-    uint64_t _lastHeardMicrostamp;
+    quint64 _wakeMicrostamp;
+    quint64 _lastHeardMicrostamp;
     HifiSockAddr _publicSocket;
     HifiSockAddr _localSocket;
     HifiSockAddr* _activeSocket;
diff --git a/libraries/shared/src/NodeList.cpp b/libraries/shared/src/NodeList.cpp
index 5fcd4d4460..e26185b8ef 100644
--- a/libraries/shared/src/NodeList.cpp
+++ b/libraries/shared/src/NodeList.cpp
@@ -128,7 +128,7 @@ void NodeList::timePingReply(const QByteArray& packet) {
         
         // The other node's expected time should be our original time plus the one way flight time
         // anything other than that is clock skew
-        uint64_t othersExprectedReply = ourOriginalTime + oneWayFlightTime;
+        quint64 othersExprectedReply = ourOriginalTime + oneWayFlightTime;
         int clockSkew = othersReplyTime - othersExprectedReply;
         
         matchingNode->setPingMs(pingTime / 1000);
diff --git a/libraries/shared/src/NodeList.h b/libraries/shared/src/NodeList.h
index f978c5479e..69c7303c7b 100644
--- a/libraries/shared/src/NodeList.h
+++ b/libraries/shared/src/NodeList.h
@@ -35,9 +35,9 @@ const int NODES_PER_BUCKET = 100;
 
 const int MAX_PACKET_SIZE = 1500;
 
-const uint64_t NODE_SILENCE_THRESHOLD_USECS = 2 * 1000 * 1000;
-const uint64_t DOMAIN_SERVER_CHECK_IN_USECS = 1 * 1000000;
-const uint64_t PING_INACTIVE_NODE_INTERVAL_USECS = 1 * 1000 * 1000;
+const quint64 NODE_SILENCE_THRESHOLD_USECS = 2 * 1000 * 1000;
+const quint64 DOMAIN_SERVER_CHECK_IN_USECS = 1 * 1000000;
+const quint64 PING_INACTIVE_NODE_INTERVAL_USECS = 1 * 1000 * 1000;
 
 extern const char SOLO_NODE_TYPES[2];
 
diff --git a/libraries/shared/src/PacketSender.cpp b/libraries/shared/src/PacketSender.cpp
index 0cc37f356e..8a031cbc39 100644
--- a/libraries/shared/src/PacketSender.cpp
+++ b/libraries/shared/src/PacketSender.cpp
@@ -16,8 +16,8 @@
 #include "PacketSender.h"
 #include "SharedUtil.h"
 
-const uint64_t PacketSender::USECS_PER_SECOND = 1000 * 1000;
-const uint64_t PacketSender::SENDING_INTERVAL_ADJUST = 200; // approaximate 200us
+const quint64 PacketSender::USECS_PER_SECOND = 1000 * 1000;
+const quint64 PacketSender::SENDING_INTERVAL_ADJUST = 200; // approaximate 200us
 const int PacketSender::TARGET_FPS = 60;
 const int PacketSender::MAX_SLEEP_INTERVAL = PacketSender::USECS_PER_SECOND;
 
@@ -82,13 +82,13 @@ bool PacketSender::threadedProcess() {
         int packetsPerSecondTarget = (_packetsPerSecond > MINIMUM_PACKETS_PER_SECOND)
                                             ? _packetsPerSecond : MINIMUM_PACKETS_PER_SECOND;
 
-        uint64_t intervalBetweenSends = USECS_PER_SECOND / packetsPerSecondTarget;
-        uint64_t sleepInterval = (intervalBetweenSends > SENDING_INTERVAL_ADJUST) ?
+        quint64 intervalBetweenSends = USECS_PER_SECOND / packetsPerSecondTarget;
+        quint64 sleepInterval = (intervalBetweenSends > SENDING_INTERVAL_ADJUST) ?
                     intervalBetweenSends - SENDING_INTERVAL_ADJUST : intervalBetweenSends;
 
         // We'll sleep before we send, this way, we can set our last send time to be our ACTUAL last send time
-        uint64_t now = usecTimestampNow();
-        uint64_t elapsed = now - _lastSendTime;
+        quint64 now = usecTimestampNow();
+        quint64 elapsed = now - _lastSendTime;
         int usecToSleep =  sleepInterval - elapsed;
 
         // If we've never sent, or it's been a long time since we sent, then our elapsed time will be quite large
@@ -132,18 +132,18 @@ bool PacketSender::threadedProcess() {
 // We also keep a running total of packets sent over multiple calls to process() so that we can adjust up or down for
 // possible rounding error that would occur if we only considered whole integer packet counts per call to process
 bool PacketSender::nonThreadedProcess() {
-    uint64_t now = usecTimestampNow();
+    quint64 now = usecTimestampNow();
 
     if (_lastProcessCallTime == 0) {
         _lastProcessCallTime = now - _usecsPerProcessCallHint;
     }
 
-    const uint64_t MINIMUM_POSSIBLE_CALL_TIME = 10; // in usecs
-    const uint64_t USECS_PER_SECOND = 1000 * 1000;
+    const quint64 MINIMUM_POSSIBLE_CALL_TIME = 10; // in usecs
+    const quint64 USECS_PER_SECOND = 1000 * 1000;
     const float ZERO_RESET_CALLS_PER_SECOND = 1; // used in guard against divide by zero
 
     // keep track of our process call times, so we have a reliable account of how often our caller calls us
-    uint64_t elapsedSinceLastCall = now - _lastProcessCallTime;
+    quint64 elapsedSinceLastCall = now - _lastProcessCallTime;
     _lastProcessCallTime = now;
     _averageProcessCallTime.updateAverage(elapsedSinceLastCall);
 
@@ -165,7 +165,7 @@ bool PacketSender::nonThreadedProcess() {
     if (_lastPPSCheck == 0) {
         _lastPPSCheck = now;
         // pretend like our lifetime began once call cycle for now, this makes our lifetime PPS start out most accurately
-        _started = now - (uint64_t)averageCallTime;
+        _started = now - (quint64)averageCallTime;
     }
 
 
@@ -215,7 +215,7 @@ bool PacketSender::nonThreadedProcess() {
 
     // So no mater whether or not we're getting called more or less than once per second, we still need to do some bookkeeping
     // to make sure we send a few extra packets to even out our flow rate.
-    uint64_t elapsedSinceLastCheck = now - _lastPPSCheck;
+    quint64 elapsedSinceLastCheck = now - _lastPPSCheck;
 
     // we might want to tun this in the future and only check after a certain number of call intervals. for now we check
     // each time and adjust accordingly
diff --git a/libraries/shared/src/PacketSender.h b/libraries/shared/src/PacketSender.h
index 415e084141..4a1e62bd0c 100644
--- a/libraries/shared/src/PacketSender.h
+++ b/libraries/shared/src/PacketSender.h
@@ -20,8 +20,8 @@ class PacketSender : public GenericThread {
     Q_OBJECT
 public:
 
-    static const uint64_t USECS_PER_SECOND;
-    static const uint64_t SENDING_INTERVAL_ADJUST;
+    static const quint64 USECS_PER_SECOND;
+    static const quint64 SENDING_INTERVAL_ADJUST;
     static const int TARGET_FPS;
     static const int MAX_SLEEP_INTERVAL;
 
@@ -72,46 +72,46 @@ public:
         { return getLifetimeInSeconds() == 0 ? 0 : (float)((float)_totalBytesQueued / getLifetimeInSeconds()); }
 
     /// returns lifetime of this object from first packet sent to now in usecs
-    uint64_t getLifetimeInUsecs() const { return (usecTimestampNow() - _started); }
+    quint64 getLifetimeInUsecs() const { return (usecTimestampNow() - _started); }
 
     /// returns lifetime of this object from first packet sent to now in usecs
     float getLifetimeInSeconds() const { return ((float)getLifetimeInUsecs() / (float)USECS_PER_SECOND); }
 
     /// returns the total packets sent by this object over its lifetime
-    uint64_t getLifetimePacketsSent() const { return _totalPacketsSent; }
+    quint64 getLifetimePacketsSent() const { return _totalPacketsSent; }
 
     /// returns the total bytes sent by this object over its lifetime
-    uint64_t getLifetimeBytesSent() const { return _totalBytesSent; }
+    quint64 getLifetimeBytesSent() const { return _totalBytesSent; }
 
     /// returns the total packets queued by this object over its lifetime
-    uint64_t getLifetimePacketsQueued() const { return _totalPacketsQueued; }
+    quint64 getLifetimePacketsQueued() const { return _totalPacketsQueued; }
 
     /// returns the total bytes queued by this object over its lifetime
-    uint64_t getLifetimeBytesQueued() const { return _totalBytesQueued; }
+    quint64 getLifetimeBytesQueued() const { return _totalBytesQueued; }
 signals:
     void packetSent(quint64);
 protected:
     int _packetsPerSecond;
     int _usecsPerProcessCallHint;
-    uint64_t _lastProcessCallTime;
+    quint64 _lastProcessCallTime;
     SimpleMovingAverage _averageProcessCallTime;
 
 private:
     std::vector _packets;
-    uint64_t _lastSendTime;
+    quint64 _lastSendTime;
 
     bool threadedProcess();
     bool nonThreadedProcess();
 
-    uint64_t _lastPPSCheck;
+    quint64 _lastPPSCheck;
     int _packetsOverCheckInterval;
 
-    uint64_t _started;
-    uint64_t _totalPacketsSent;
-    uint64_t _totalBytesSent;
+    quint64 _started;
+    quint64 _totalPacketsSent;
+    quint64 _totalBytesSent;
 
-    uint64_t _totalPacketsQueued;
-    uint64_t _totalBytesQueued;
+    quint64 _totalPacketsQueued;
+    quint64 _totalBytesQueued;
 };
 
 #endif // __shared__PacketSender__
diff --git a/libraries/shared/src/PerfStat.cpp b/libraries/shared/src/PerfStat.cpp
index b99b323751..7bea51dd6e 100644
--- a/libraries/shared/src/PerfStat.cpp
+++ b/libraries/shared/src/PerfStat.cpp
@@ -23,8 +23,8 @@ bool PerformanceWarning::_suppressShortTimings = false;
 
 // Destructor handles recording all of our stats
 PerformanceWarning::~PerformanceWarning() {
-    uint64_t end = usecTimestampNow();
-    uint64_t elapsedusec = (end - _start);
+    quint64 end = usecTimestampNow();
+    quint64 elapsedusec = (end - _start);
     double elapsedmsec = elapsedusec / 1000.0;
     if ((_alwaysDisplay || _renderWarningsOn) && elapsedmsec > 1) {
         if (elapsedmsec > 1000) {
diff --git a/libraries/shared/src/PerfStat.h b/libraries/shared/src/PerfStat.h
index 2e56526495..fffb095021 100644
--- a/libraries/shared/src/PerfStat.h
+++ b/libraries/shared/src/PerfStat.h
@@ -28,17 +28,17 @@
 
 class PerformanceWarning {
 private:
-	uint64_t _start;
+	quint64 _start;
 	const char* _message;
 	bool _renderWarningsOn;
 	bool _alwaysDisplay;
-	uint64_t* _runningTotal;
-	uint64_t* _totalCalls;
+	quint64* _runningTotal;
+	quint64* _totalCalls;
 	static bool _suppressShortTimings;
 public:
 
     PerformanceWarning(bool renderWarnings, const char* message, bool alwaysDisplay = false,
-                        uint64_t* runningTotal = NULL, uint64_t* totalCalls = NULL) :
+                        quint64* runningTotal = NULL, quint64* totalCalls = NULL) :
         _start(usecTimestampNow()),
         _message(message),
         _renderWarningsOn(renderWarnings),
diff --git a/libraries/shared/src/Radix2IntegerScanner.h b/libraries/shared/src/Radix2IntegerScanner.h
index 355ecfef46..84e7c7077e 100644
--- a/libraries/shared/src/Radix2IntegerScanner.h
+++ b/libraries/shared/src/Radix2IntegerScanner.h
@@ -25,7 +25,7 @@ namespace type_traits { // those are needed for the declaration, see below
     template< typename T > struct make_unsigned< T, 1 > { typedef uint8_t type; };
     template< typename T > struct make_unsigned< T, 2 > { typedef uint16_t type; };
     template< typename T > struct make_unsigned< T, 4 > { typedef uint32_t type; };
-    template< typename T > struct make_unsigned< T, 8 > { typedef uint64_t type; };
+    template< typename T > struct make_unsigned< T, 8 > { typedef quint64 type; };
 }
 
 
diff --git a/libraries/shared/src/ReceivedPacketProcessor.cpp b/libraries/shared/src/ReceivedPacketProcessor.cpp
index a34e41006e..5faec02ea1 100644
--- a/libraries/shared/src/ReceivedPacketProcessor.cpp
+++ b/libraries/shared/src/ReceivedPacketProcessor.cpp
@@ -34,7 +34,7 @@ bool ReceivedPacketProcessor::process() {
     // If a derived class handles process sleeping, like the JurisdiciontListener, then it can set
     // this _dontSleep member and we will honor that request.
     if (_packets.size() == 0 && !_dontSleep) {
-        const uint64_t RECEIVED_THREAD_SLEEP_INTERVAL = (1000 * 1000)/60; // check at 60fps
+        const quint64 RECEIVED_THREAD_SLEEP_INTERVAL = (1000 * 1000)/60; // check at 60fps
         usleep(RECEIVED_THREAD_SLEEP_INTERVAL);
     }
     while (_packets.size() > 0) {
diff --git a/libraries/shared/src/SharedUtil.cpp b/libraries/shared/src/SharedUtil.cpp
index 9430fcde20..44239c7c07 100644
--- a/libraries/shared/src/SharedUtil.cpp
+++ b/libraries/shared/src/SharedUtil.cpp
@@ -26,7 +26,7 @@
 #include "PacketHeaders.h"
 #include "SharedUtil.h"
 
-uint64_t usecTimestamp(const timeval *time) {
+quint64 usecTimestamp(const timeval *time) {
     return (time->tv_sec * 1000000 + time->tv_usec);
 }
 
@@ -35,7 +35,7 @@ void usecTimestampNowForceClockSkew(int clockSkew) {
     ::usecTimestampNowAdjust = clockSkew;
 }
 
-uint64_t usecTimestampNow() {
+quint64 usecTimestampNow() {
     timeval now;
     gettimeofday(&now, NULL);
     return (now.tv_sec * 1000000 + now.tv_usec) + ::usecTimestampNowAdjust;
diff --git a/libraries/shared/src/SharedUtil.h b/libraries/shared/src/SharedUtil.h
index 6498962fad..e95aaf980c 100644
--- a/libraries/shared/src/SharedUtil.h
+++ b/libraries/shared/src/SharedUtil.h
@@ -57,12 +57,12 @@ static const float METER            = 1.0f;
 static const float DECIMETER        = 0.1f;
 static const float CENTIMETER       = 0.01f;
 static const float MILLIIMETER      = 0.001f;
-static const uint64_t USECS_PER_MSEC = 1000;
-static const uint64_t MSECS_PER_SECOND = 1000;
-static const uint64_t USECS_PER_SECOND = USECS_PER_MSEC * MSECS_PER_SECOND;
+static const quint64 USECS_PER_MSEC = 1000;
+static const quint64 MSECS_PER_SECOND = 1000;
+static const quint64 USECS_PER_SECOND = USECS_PER_MSEC * MSECS_PER_SECOND;
 
-uint64_t usecTimestamp(const timeval *time);
-uint64_t usecTimestampNow();
+quint64 usecTimestamp(const timeval *time);
+quint64 usecTimestampNow();
 void usecTimestampNowForceClockSkew(int clockSkew);
 
 float randFloat();
diff --git a/libraries/shared/src/SimpleMovingAverage.h b/libraries/shared/src/SimpleMovingAverage.h
index 9788aafe58..2f2b45100c 100644
--- a/libraries/shared/src/SimpleMovingAverage.h
+++ b/libraries/shared/src/SimpleMovingAverage.h
@@ -26,7 +26,7 @@ public:
     float getAverageSampleValuePerSecond();
 private:
     int _numSamples;
-    uint64_t _lastEventTimestamp;
+    quint64 _lastEventTimestamp;
     float _average;
     float _eventDeltaAverage;
     
diff --git a/libraries/voxels/src/VoxelConstants.h b/libraries/voxels/src/VoxelConstants.h
index b57562f15e..d4cbc54f18 100644
--- a/libraries/voxels/src/VoxelConstants.h
+++ b/libraries/voxels/src/VoxelConstants.h
@@ -40,7 +40,7 @@ const glBufferIndex GLBUFFER_INDEX_UNKNOWN = ULONG_MAX;
 const float SIXTY_FPS_IN_MILLISECONDS = 1000.0f / 60.0f;
 const float VIEW_CULLING_RATE_IN_MILLISECONDS = 1000.0f; // once a second is fine
 
-const uint64_t CLIENT_TO_SERVER_VOXEL_SEND_INTERVAL_USECS = 1000 * 5; // 1 packet every 50 milliseconds
+const quint64 CLIENT_TO_SERVER_VOXEL_SEND_INTERVAL_USECS = 1000 * 5; // 1 packet every 50 milliseconds
 
 
 const int DEFAULT_MAX_VOXEL_PPS = 600; // the default maximum PPS we think a voxel server should send to a client
diff --git a/libraries/voxels/src/VoxelEditPacketSender.cpp b/libraries/voxels/src/VoxelEditPacketSender.cpp
index c0477b683b..3ea4ca3626 100644
--- a/libraries/voxels/src/VoxelEditPacketSender.cpp
+++ b/libraries/voxels/src/VoxelEditPacketSender.cpp
@@ -44,8 +44,8 @@ bool createVoxelEditMessage(PacketType command, short int sequence,
     *sequenceAt = sequence;
     
     // pack in timestamp
-    uint64_t now = usecTimestampNow();
-    uint64_t* timeAt = (uint64_t*)&messageBuffer[numBytesPacketHeader + sizeof(sequence)];
+    quint64 now = usecTimestampNow();
+    quint64* timeAt = (quint64*)&messageBuffer[numBytesPacketHeader + sizeof(sequence)];
     *timeAt = now;
     
     unsigned char* copyAt = &messageBuffer[numBytesPacketHeader + sizeof(sequence) + sizeof(now)];
diff --git a/libraries/voxels/src/VoxelPacketData.h b/libraries/voxels/src/VoxelPacketData.h
index 5cdc314503..088a69b970 100644
--- a/libraries/voxels/src/VoxelPacketData.h
+++ b/libraries/voxels/src/VoxelPacketData.h
@@ -28,7 +28,7 @@
 
 typedef unsigned char VOXEL_PACKET_FLAGS;
 typedef uint16_t VOXEL_PACKET_SEQUENCE;
-typedef uint64_t VOXEL_PACKET_SENT_TIME;
+typedef quint64 VOXEL_PACKET_SENT_TIME;
 typedef uint16_t VOXEL_PACKET_INTERNAL_SECTION_SIZE;
 const int MAX_VOXEL_PACKET_SIZE = MAX_PACKET_SIZE;
 

From 8384ff79dfbb8b7fdc465b2f46b8c34adc794841 Mon Sep 17 00:00:00 2001
From: Stephen Birarda 
Date: Tue, 28 Jan 2014 12:36:43 -0800
Subject: [PATCH 10/16] remove one Qt type replacement

---
 libraries/shared/src/SimpleMovingAverage.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/libraries/shared/src/SimpleMovingAverage.h b/libraries/shared/src/SimpleMovingAverage.h
index 2f2b45100c..9788aafe58 100644
--- a/libraries/shared/src/SimpleMovingAverage.h
+++ b/libraries/shared/src/SimpleMovingAverage.h
@@ -26,7 +26,7 @@ public:
     float getAverageSampleValuePerSecond();
 private:
     int _numSamples;
-    quint64 _lastEventTimestamp;
+    uint64_t _lastEventTimestamp;
     float _average;
     float _eventDeltaAverage;
     

From fe410ae3e98513d61850e6f6c7db1b47a4ee0d33 Mon Sep 17 00:00:00 2001
From: Stephen Birarda 
Date: Tue, 28 Jan 2014 12:56:05 -0800
Subject: [PATCH 11/16] fix packet header size constraints

---
 libraries/octree/src/OctreePacketData.h | 4 ++--
 libraries/shared/src/PacketHeaders.cpp  | 7 ++-----
 libraries/shared/src/PacketHeaders.h    | 4 ++++
 libraries/voxels/src/VoxelPacketData.h  | 4 ++--
 4 files changed, 10 insertions(+), 9 deletions(-)

diff --git a/libraries/octree/src/OctreePacketData.h b/libraries/octree/src/OctreePacketData.h
index 9ef7399fe0..448c350d3a 100644
--- a/libraries/octree/src/OctreePacketData.h
+++ b/libraries/octree/src/OctreePacketData.h
@@ -30,8 +30,8 @@ typedef uint16_t OCTREE_PACKET_INTERNAL_SECTION_SIZE;
 const int MAX_OCTREE_PACKET_SIZE = MAX_PACKET_SIZE;
 
 // this is overly conservative - sizeof(PacketType) is 8 bytes but a packed PacketType could be as small as one byte
-const int OCTREE_PACKET_HEADER_SIZE = (sizeof(PacketType) + sizeof(PacketVersion) + sizeof(OCTREE_PACKET_FLAGS)
-                + sizeof(OCTREE_PACKET_SEQUENCE) + sizeof(OCTREE_PACKET_SENT_TIME));
+const int OCTREE_PACKET_HEADER_SIZE = MAX_PACKET_HEADER_BYTES +  sizeof(OCTREE_PACKET_FLAGS)
+                + sizeof(OCTREE_PACKET_SEQUENCE) + sizeof(OCTREE_PACKET_SENT_TIME);
 
 const int MAX_OCTREE_PACKET_DATA_SIZE = MAX_PACKET_SIZE - OCTREE_PACKET_HEADER_SIZE;
             
diff --git a/libraries/shared/src/PacketHeaders.cpp b/libraries/shared/src/PacketHeaders.cpp
index 545c779fea..5d2dd52a2f 100644
--- a/libraries/shared/src/PacketHeaders.cpp
+++ b/libraries/shared/src/PacketHeaders.cpp
@@ -11,7 +11,6 @@
 #include 
 
 #include "NodeList.h"
-#include "UUID.h"
 
 #include "PacketHeaders.h"
 
@@ -50,10 +49,8 @@ PacketVersion versionForPacketType(PacketType type) {
     }
 }
 
-const int MAX_HEADER_BYTES = sizeof(PacketType) + sizeof(PacketVersion) + NUM_BYTES_RFC4122_UUID;
-
 QByteArray byteArrayWithPopluatedHeader(PacketType type, const QUuid& connectionUUID) {
-    QByteArray freshByteArray(MAX_HEADER_BYTES, 0);
+    QByteArray freshByteArray(MAX_PACKET_HEADER_BYTES, 0);
     freshByteArray.resize(populatePacketHeader(freshByteArray, type, connectionUUID));
     return freshByteArray;
 }
@@ -73,7 +70,7 @@ int populatePacketHeader(char* packet, PacketType type, const QUuid& connectionU
     QUuid packUUID = connectionUUID.isNull() ? NodeList::getInstance()->getOwnerUUID() : connectionUUID;
     
     QByteArray rfcUUID = packUUID.toRfc4122();
-    memcpy(packet + numTypeBytes + sizeof(PacketVersion), rfcUUID, NUM_BYTES_RFC4122_UUID);
+    memcpy(packet + numTypeBytes + sizeof(PacketVersion), rfcUUID.constData(), NUM_BYTES_RFC4122_UUID);
     
     // return the number of bytes written for pointer pushing
     return numTypeBytes + sizeof(PacketVersion) + NUM_BYTES_RFC4122_UUID;
diff --git a/libraries/shared/src/PacketHeaders.h b/libraries/shared/src/PacketHeaders.h
index e194406d58..543dce0504 100644
--- a/libraries/shared/src/PacketHeaders.h
+++ b/libraries/shared/src/PacketHeaders.h
@@ -14,6 +14,8 @@
 
 #include 
 
+#include "UUID.h"
+
 enum PacketType {
     PacketTypeUnknown,
     PacketTypeStunResponse,
@@ -54,6 +56,8 @@ enum PacketType {
 
 typedef char PacketVersion;
 
+const int MAX_PACKET_HEADER_BYTES = sizeof(PacketType) + sizeof(PacketVersion) + NUM_BYTES_RFC4122_UUID;;
+
 PacketVersion versionForPacketType(PacketType type);
 
 const QUuid nullUUID = QUuid();
diff --git a/libraries/voxels/src/VoxelPacketData.h b/libraries/voxels/src/VoxelPacketData.h
index 088a69b970..bf2a759225 100644
--- a/libraries/voxels/src/VoxelPacketData.h
+++ b/libraries/voxels/src/VoxelPacketData.h
@@ -33,8 +33,8 @@ typedef uint16_t VOXEL_PACKET_INTERNAL_SECTION_SIZE;
 const int MAX_VOXEL_PACKET_SIZE = MAX_PACKET_SIZE;
 
 // this is overly conservative - uses 8 bytes for PacketType which could be as compact as a single byte
-const int VOXEL_PACKET_HEADER_SIZE = (sizeof(PacketType) + sizeof(PacketVersion) + sizeof(VOXEL_PACKET_FLAGS) 
-                + sizeof(VOXEL_PACKET_SEQUENCE) + sizeof(VOXEL_PACKET_SENT_TIME));
+const int VOXEL_PACKET_HEADER_SIZE = MAX_PACKET_HEADER_BYTES + sizeof(VOXEL_PACKET_FLAGS)
+                + sizeof(VOXEL_PACKET_SEQUENCE) + sizeof(VOXEL_PACKET_SENT_TIME);
 
 const int MAX_VOXEL_PACKET_DATA_SIZE = MAX_PACKET_SIZE - VOXEL_PACKET_HEADER_SIZE;
             

From 4de270b8323d518ceb8ef4cf2a5a41cbad6777bb Mon Sep 17 00:00:00 2001
From: Stephen Birarda 
Date: Tue, 28 Jan 2014 13:38:33 -0800
Subject: [PATCH 12/16] cleanup Node types, closes #1726

---
 animation-server/src/AnimationServer.cpp      |  6 +-
 assignment-client/src/Agent.cpp               |  8 +--
 assignment-client/src/AssignmentClient.cpp    |  4 +-
 assignment-client/src/audio/AudioMixer.cpp    |  6 +-
 assignment-client/src/avatars/AvatarMixer.cpp | 10 +--
 .../src/metavoxels/MetavoxelServer.cpp        |  2 +-
 domain-server/src/DomainServer.cpp            | 16 ++---
 domain-server/src/DomainServer.h              |  2 +-
 interface/src/Application.cpp                 | 54 ++++++++--------
 interface/src/Application.h                   |  4 +-
 interface/src/Audio.cpp                       |  2 +-
 interface/src/MetavoxelSystem.cpp             |  4 +-
 interface/src/ParticleTreeRenderer.h          |  2 +-
 interface/src/VoxelSystem.cpp                 |  6 +-
 interface/src/avatar/MyAvatar.cpp             |  2 +-
 interface/src/ui/VoxelStatsDialog.cpp         |  8 +--
 interface/src/ui/VoxelStatsDialog.h           |  2 +-
 libraries/audio/src/AudioInjector.cpp         |  2 +-
 libraries/octree-server/src/OctreeServer.cpp  |  4 +-
 libraries/octree/src/JurisdictionListener.cpp |  4 +-
 libraries/octree/src/JurisdictionListener.h   |  8 +--
 libraries/octree/src/JurisdictionMap.cpp      |  6 +-
 libraries/octree/src/JurisdictionMap.h        | 10 +--
 libraries/octree/src/JurisdictionSender.cpp   |  2 +-
 libraries/octree/src/JurisdictionSender.h     |  8 +--
 libraries/octree/src/OctreeRenderer.h         |  2 +-
 .../octree/src/OctreeScriptingInterface.h     |  2 +-
 .../particle-server/src/ParticleServer.h      |  2 +-
 .../particles/src/ParticleCollisionSystem.cpp |  2 +-
 .../particles/src/ParticleEditPacketSender.h  |  2 +-
 .../src/ParticlesScriptingInterface.h         |  2 +-
 libraries/script-engine/src/ScriptEngine.cpp  |  2 +-
 libraries/shared/src/Assignment.cpp           | 14 ++---
 libraries/shared/src/Assignment.h             |  2 +-
 libraries/shared/src/Node.cpp                 | 63 +++++++------------
 libraries/shared/src/Node.h                   | 32 ++++++----
 libraries/shared/src/NodeList.cpp             | 20 +++---
 libraries/shared/src/NodeList.h               | 21 +++----
 libraries/shared/src/ThreadedAssignment.cpp   |  2 +-
 libraries/shared/src/ThreadedAssignment.h     |  2 +-
 libraries/voxel-server/src/VoxelServer.cpp    |  2 +-
 libraries/voxel-server/src/VoxelServer.h      |  2 +-
 libraries/voxels/src/VoxelEditPacketSender.h  |  2 +-
 .../voxels/src/VoxelsScriptingInterface.h     |  2 +-
 44 files changed, 176 insertions(+), 184 deletions(-)

diff --git a/animation-server/src/AnimationServer.cpp b/animation-server/src/AnimationServer.cpp
index 52c281c0d9..24ea7ede9c 100644
--- a/animation-server/src/AnimationServer.cpp
+++ b/animation-server/src/AnimationServer.cpp
@@ -694,7 +694,7 @@ AnimationServer::AnimationServer(int &argc, char **argv) :
 {
     ::start = usecTimestampNow();
     
-    NodeList* nodeList = NodeList::createInstance(NODE_TYPE_ANIMATION_SERVER, ANIMATION_LISTEN_PORT);
+    NodeList* nodeList = NodeList::createInstance(NodeType::AnimationServer, ANIMATION_LISTEN_PORT);
     setvbuf(stdout, NULL, _IOLBF, 0);
     
     // Handle Local Domain testing with the --local command line
@@ -806,7 +806,7 @@ AnimationServer::AnimationServer(int &argc, char **argv) :
     
     pthread_create(&::animateVoxelThread, NULL, animateVoxels, NULL);
 
-    NodeList::getInstance()->addNodeTypeToInterestSet(NODE_TYPE_VOXEL_SERVER);
+    NodeList::getInstance()->addNodeTypeToInterestSet(NodeType::VoxelServer);
     
     QTimer* domainServerTimer = new QTimer(this);
     connect(domainServerTimer, SIGNAL(timeout()), nodeList, SLOT(sendDomainServerCheckIn()));
@@ -834,7 +834,7 @@ void AnimationServer::readPendingDatagrams() {
             if (packetTypeForPacket(receivedPacket) == PacketTypeJurisdiction) {
                 int headerBytes = numBytesForPacketHeader(receivedPacket);
                 // PacketType_JURISDICTION, first byte is the node type...
-                if (receivedPacket.data()[headerBytes] == NODE_TYPE_VOXEL_SERVER && ::jurisdictionListener) {
+                if (receivedPacket.data()[headerBytes] == NodeType::VoxelServer && ::jurisdictionListener) {
                     ::jurisdictionListener->queueReceivedPacket(nodeSockAddr, receivedPacket);
                 }
             }
diff --git a/assignment-client/src/Agent.cpp b/assignment-client/src/Agent.cpp
index 38985a916e..85d996511e 100644
--- a/assignment-client/src/Agent.cpp
+++ b/assignment-client/src/Agent.cpp
@@ -32,11 +32,11 @@ void Agent::processDatagram(const QByteArray& dataByteArray, const HifiSockAddr&
         int headerBytes = numBytesForPacketHeader(dataByteArray);
         // PacketType_JURISDICTION, first byte is the node type...
         switch (dataByteArray[headerBytes]) {
-            case NODE_TYPE_VOXEL_SERVER:
+            case NodeType::VoxelServer:
                 _scriptEngine.getVoxelsScriptingInterface()->getJurisdictionListener()->queueReceivedPacket(senderSockAddr,
                                                                                                             dataByteArray);
                 break;
-            case NODE_TYPE_PARTICLE_SERVER:
+            case NodeType::ParticleServer:
                 _scriptEngine.getParticlesScriptingInterface()->getJurisdictionListener()->queueReceivedPacket(senderSockAddr,
                                                                                                                dataByteArray);
                 break;
@@ -48,9 +48,9 @@ void Agent::processDatagram(const QByteArray& dataByteArray, const HifiSockAddr&
 
 void Agent::run() {
     NodeList* nodeList = NodeList::getInstance();
-    nodeList->setOwnerType(NODE_TYPE_AGENT);
+    nodeList->setOwnerType(NodeType::Agent);
     
-    nodeList->addSetOfNodeTypesToNodeInterestSet(QSet() << NODE_TYPE_AUDIO_MIXER << NODE_TYPE_AVATAR_MIXER);
+    nodeList->addSetOfNodeTypesToNodeInterestSet(NodeSet() << NodeType::AudioMixer << NodeType::AvatarMixer);
     
     // figure out the URL for the script for this agent assignment
     QString scriptURLString("http://%1:8080/assignment/%2");
diff --git a/assignment-client/src/AssignmentClient.cpp b/assignment-client/src/AssignmentClient.cpp
index 8725c6ca56..cdf0da43de 100644
--- a/assignment-client/src/AssignmentClient.cpp
+++ b/assignment-client/src/AssignmentClient.cpp
@@ -52,7 +52,7 @@ AssignmentClient::AssignmentClient(int &argc, char **argv) :
     _requestAssignment = Assignment(Assignment::RequestCommand, requestAssignmentType, requestAssignmentPool);
     
     // create a NodeList as an unassigned client
-    NodeList* nodeList = NodeList::createInstance(NODE_TYPE_UNASSIGNED);
+    NodeList* nodeList = NodeList::createInstance(NodeType::Unassigned);
     
     const char CUSTOM_ASSIGNMENT_SERVER_HOSTNAME_OPTION[] = "-a";
     const char CUSTOM_ASSIGNMENT_SERVER_PORT_OPTION[] = "-p";
@@ -174,6 +174,6 @@ void AssignmentClient::assignmentCompleted() {
     NodeList* nodeList = NodeList::getInstance();
     
     // reset our NodeList by switching back to unassigned and clearing the list
-    nodeList->setOwnerType(NODE_TYPE_UNASSIGNED);
+    nodeList->setOwnerType(NodeType::Unassigned);
     nodeList->reset();
 }
diff --git a/assignment-client/src/audio/AudioMixer.cpp b/assignment-client/src/audio/AudioMixer.cpp
index 6a721824f3..90e2810f27 100644
--- a/assignment-client/src/audio/AudioMixer.cpp
+++ b/assignment-client/src/audio/AudioMixer.cpp
@@ -237,11 +237,11 @@ void AudioMixer::processDatagram(const QByteArray& dataByteArray, const HifiSock
 
 void AudioMixer::run() {
 
-    commonInit(AUDIO_MIXER_LOGGING_TARGET_NAME, NODE_TYPE_AUDIO_MIXER);
+    commonInit(AUDIO_MIXER_LOGGING_TARGET_NAME, NodeType::AudioMixer);
 
     NodeList* nodeList = NodeList::getInstance();
 
-    nodeList->addNodeTypeToInterestSet(NODE_TYPE_AGENT);
+    nodeList->addNodeTypeToInterestSet(NodeType::Agent);
 
     nodeList->linkedDataCreateCallback = attachNewBufferToNode;
 
@@ -274,7 +274,7 @@ void AudioMixer::run() {
         }
 
         foreach (const SharedNodePointer& node, nodeList->getNodeHash()) {
-            if (node->getType() == NODE_TYPE_AGENT && node->getActiveSocket() && node->getLinkedData()
+            if (node->getType() == NodeType::Agent && node->getActiveSocket() && node->getLinkedData()
                 && ((AudioMixerClientData*) node->getLinkedData())->getAvatarAudioRingBuffer()) {
                 prepareMixForListeningNode(node.data());
 
diff --git a/assignment-client/src/avatars/AvatarMixer.cpp b/assignment-client/src/avatars/AvatarMixer.cpp
index bb5654ddb7..014008d35e 100644
--- a/assignment-client/src/avatars/AvatarMixer.cpp
+++ b/assignment-client/src/avatars/AvatarMixer.cpp
@@ -57,7 +57,7 @@ void broadcastAvatarData() {
     NodeList* nodeList = NodeList::getInstance();
     
     foreach (const SharedNodePointer& node, nodeList->getNodeHash()) {
-        if (node->getLinkedData() && node->getType() == NODE_TYPE_AGENT && node->getActiveSocket()) {
+        if (node->getLinkedData() && node->getType() == NodeType::Agent && node->getActiveSocket()) {
             
             // reset packet pointers for this node
             mixedAvatarByteArray.resize(numPacketHeaderBytes);
@@ -100,7 +100,7 @@ void broadcastAvatarData() {
 }
 
 void AvatarMixer::nodeKilled(SharedNodePointer killedNode) {
-    if (killedNode->getType() == NODE_TYPE_AGENT
+    if (killedNode->getType() == NodeType::Agent
         && killedNode->getLinkedData()) {
         // this was an avatar we were sending to other people
         // send a kill packet for it to our other nodes
@@ -108,7 +108,7 @@ void AvatarMixer::nodeKilled(SharedNodePointer killedNode) {
         killPacket += killedNode->getUUID().toRfc4122();
         
         NodeList::getInstance()->broadcastToNodes(killPacket,
-                                                  QSet() << NODE_TYPE_AGENT);
+                                                  NodeSet() << NodeType::Agent);
     }
 }
 
@@ -144,10 +144,10 @@ void AvatarMixer::processDatagram(const QByteArray& dataByteArray, const HifiSoc
 }
 
 void AvatarMixer::run() {
-    commonInit(AVATAR_MIXER_LOGGING_NAME, NODE_TYPE_AVATAR_MIXER);
+    commonInit(AVATAR_MIXER_LOGGING_NAME, NodeType::AvatarMixer);
     
     NodeList* nodeList = NodeList::getInstance();
-    nodeList->addNodeTypeToInterestSet(NODE_TYPE_AGENT);
+    nodeList->addNodeTypeToInterestSet(NodeType::Agent);
     
     nodeList->linkedDataCreateCallback = attachAvatarDataToNode;
     
diff --git a/assignment-client/src/metavoxels/MetavoxelServer.cpp b/assignment-client/src/metavoxels/MetavoxelServer.cpp
index 9fee6f3e2c..59b08a7185 100644
--- a/assignment-client/src/metavoxels/MetavoxelServer.cpp
+++ b/assignment-client/src/metavoxels/MetavoxelServer.cpp
@@ -32,7 +32,7 @@ void MetavoxelServer::removeSession(const QUuid& sessionId) {
 const char METAVOXEL_SERVER_LOGGING_NAME[] = "metavoxel-server";
 
 void MetavoxelServer::run() {
-    commonInit(METAVOXEL_SERVER_LOGGING_NAME, NODE_TYPE_METAVOXEL_SERVER);
+    commonInit(METAVOXEL_SERVER_LOGGING_NAME, NodeType::MetavoxelServer);
     
     _lastSend = QDateTime::currentMSecsSinceEpoch();
     _sendTimer.start(SEND_INTERVAL);
diff --git a/domain-server/src/DomainServer.cpp b/domain-server/src/DomainServer.cpp
index 908f0bacdf..c861e678a0 100644
--- a/domain-server/src/DomainServer.cpp
+++ b/domain-server/src/DomainServer.cpp
@@ -66,7 +66,7 @@ DomainServer::DomainServer(int argc, char* argv[]) :
         _metavoxelServerConfig = getCmdOption(argc, (const char**) argv, metavoxelConfigOption.constData());
     }
 
-    NodeList* nodeList = NodeList::createInstance(NODE_TYPE_DOMAIN, domainServerPort);
+    NodeList* nodeList = NodeList::createInstance(NodeType::DomainServer, domainServerPort);
 
     connect(nodeList, SIGNAL(nodeKilled(SharedNodePointer)), this, SLOT(nodeKilled(SharedNodePointer)));
 
@@ -110,7 +110,7 @@ void DomainServer::readAvailableDatagrams() {
     static int numAssignmentPacketHeaderBytes = assignmentPacket.size();
     
     QByteArray receivedPacket;
-    NODE_TYPE nodeType;
+    NodeType_t nodeType;
     QUuid nodeUUID;
 
     while (nodeList->getNodeSocket().hasPendingDatagrams()) {
@@ -144,9 +144,9 @@ void DomainServer::readAvailableDatagrams() {
                     }
                 }
                 
-                const QSet STATICALLY_ASSIGNED_NODES = QSet() << NODE_TYPE_AUDIO_MIXER
-                    << NODE_TYPE_AVATAR_MIXER << NODE_TYPE_VOXEL_SERVER << NODE_TYPE_PARTICLE_SERVER
-                    << NODE_TYPE_METAVOXEL_SERVER;
+                const QSet STATICALLY_ASSIGNED_NODES = QSet() << NodeType::AudioMixer
+                    << NodeType::AvatarMixer << NodeType::VoxelServer << NodeType::ParticleServer
+                    << NodeType::MetavoxelServer;
                 
                 Assignment* matchingStaticAssignment = NULL;
                 
@@ -183,7 +183,7 @@ void DomainServer::readAvailableDatagrams() {
                     quint8 numInterestTypes = 0;
                     packetStream >> numInterestTypes;
                     
-                    NODE_TYPE* nodeTypesOfInterest = reinterpret_cast(receivedPacket.data()
+                    NodeType_t* nodeTypesOfInterest = reinterpret_cast(receivedPacket.data()
                                                                                   + packetStream.device()->pos());
                     
                     if (numInterestTypes > 0) {
@@ -262,7 +262,7 @@ QJsonObject jsonObjectForNode(Node* node) {
     QJsonObject nodeJson;
 
     // re-format the type name so it matches the target name
-    QString nodeTypeName(node->getTypeName());
+    QString nodeTypeName = NodeType::getNodeTypeName(node->getType());
     nodeTypeName = nodeTypeName.toLower();
     nodeTypeName.replace(' ', '-');
 
@@ -642,7 +642,7 @@ void DomainServer::prepopulateStaticAssignmentFile() {
     _staticAssignmentFile.close();
 }
 
-Assignment* DomainServer::matchingStaticAssignmentForCheckIn(const QUuid& checkInUUID, NODE_TYPE nodeType) {
+Assignment* DomainServer::matchingStaticAssignmentForCheckIn(const QUuid& checkInUUID, NodeType_t nodeType) {
     // pull the UUID passed with the check in
 
     if (_hasCompletedRestartHold) {
diff --git a/domain-server/src/DomainServer.h b/domain-server/src/DomainServer.h
index 1c662bcb73..26cdc765ba 100644
--- a/domain-server/src/DomainServer.h
+++ b/domain-server/src/DomainServer.h
@@ -39,7 +39,7 @@ private:
     QString readServerAssignmentConfig(QJsonObject jsonObj, const char* nodeName);
 
     void prepopulateStaticAssignmentFile();
-    Assignment* matchingStaticAssignmentForCheckIn(const QUuid& checkInUUID, NODE_TYPE nodeType);
+    Assignment* matchingStaticAssignmentForCheckIn(const QUuid& checkInUUID, NodeType_t nodeType);
     Assignment* deployableAssignmentForRequest(Assignment& requestAssignment);
     void removeAssignmentFromQueue(Assignment* removableAssignment);
     bool checkInWithUUIDMatchesExistingNode(const HifiSockAddr& nodePublicSocket,
diff --git a/interface/src/Application.cpp b/interface/src/Application.cpp
index 892b97521a..eccf2dae10 100644
--- a/interface/src/Application.cpp
+++ b/interface/src/Application.cpp
@@ -182,7 +182,7 @@ Application::Application(int& argc, char** argv, timeval &startup_time) :
     _nodeThread->setPriority(QThread::TimeCriticalPriority);
     
     // put the NodeList and datagram processing on the node thread
-    NodeList* nodeList = NodeList::createInstance(NODE_TYPE_AGENT, listenPort);
+    NodeList* nodeList = NodeList::createInstance(NodeType::Agent, listenPort);
     
     nodeList->moveToThread(_nodeThread);
     _datagramProcessor.moveToThread(_nodeThread);
@@ -229,9 +229,9 @@ Application::Application(int& argc, char** argv, timeval &startup_time) :
     #endif
 
     // tell the NodeList instance who to tell the domain server we care about
-    nodeList->addSetOfNodeTypesToNodeInterestSet(QSet() << NODE_TYPE_AUDIO_MIXER << NODE_TYPE_AVATAR_MIXER
-                                                 << NODE_TYPE_VOXEL_SERVER << NODE_TYPE_PARTICLE_SERVER
-                                                 << NODE_TYPE_METAVOXEL_SERVER);
+    nodeList->addSetOfNodeTypesToNodeInterestSet(QSet() << NodeType::AudioMixer << NodeType::AvatarMixer
+                                                 << NodeType::VoxelServer << NodeType::ParticleServer
+                                                 << NodeType::MetavoxelServer);
     
     // connect to the packet sent signal of the _voxelEditSender and the _particleEditSender
     connect(&_voxelEditSender, &VoxelEditPacketSender::packetSent, this, &Application::packetSent);
@@ -649,24 +649,24 @@ void Application::resetProfile(const QString& username) {
 }
 
 void Application::controlledBroadcastToNodes(const QByteArray& packet,
-                                             const QSet& destinationNodeTypes) {
-    foreach(NODE_TYPE type, destinationNodeTypes) {
+                                             const QSet& destinationNodeTypes) {
+    foreach(NodeType_t type, destinationNodeTypes) {
         // Intercept data to voxel server when voxels are disabled
-        if (type == NODE_TYPE_VOXEL_SERVER && !Menu::getInstance()->isOptionChecked(MenuOption::Voxels)) {
+        if (type == NodeType::VoxelServer && !Menu::getInstance()->isOptionChecked(MenuOption::Voxels)) {
             continue;
         }
         
         // Perform the broadcast for one type
-        int nReceivingNodes = NodeList::getInstance()->broadcastToNodes(packet, QSet() << type);
+        int nReceivingNodes = NodeList::getInstance()->broadcastToNodes(packet, QSet() << type);
         
         // Feed number of bytes to corresponding channel of the bandwidth meter, if any (done otherwise)
         BandwidthMeter::ChannelIndex channel;
         switch (type) {
-            case NODE_TYPE_AGENT:
-            case NODE_TYPE_AVATAR_MIXER:
+            case NodeType::Agent:
+            case NodeType::AvatarMixer:
                 channel = BandwidthMeter::AVATARS;
                 break;
-            case NODE_TYPE_VOXEL_SERVER:
+            case NodeType::VoxelServer:
                 channel = BandwidthMeter::VOXELS;
                 break;
             default:
@@ -1332,10 +1332,10 @@ void Application::wheelEvent(QWheelEvent* event) {
 
 void Application::sendPingPackets() {
     QByteArray pingPacket = NodeList::getInstance()->constructPingPacket();
-    getInstance()->controlledBroadcastToNodes(pingPacket, QSet() << NODE_TYPE_VOXEL_SERVER
-                                              << NODE_TYPE_PARTICLE_SERVER
-                                              << NODE_TYPE_AUDIO_MIXER << NODE_TYPE_AVATAR_MIXER
-                                              << NODE_TYPE_METAVOXEL_SERVER);
+    getInstance()->controlledBroadcastToNodes(pingPacket, QSet() << NodeType::VoxelServer
+                                              << NodeType::ParticleServer
+                                              << NodeType::AudioMixer << NodeType::AvatarMixer
+                                              << NodeType::MetavoxelServer);
 }
 
 //  Every second, check the frame rates and other stuff
@@ -2363,7 +2363,7 @@ void Application::updateAvatar(float deltaTime) {
     QByteArray avatarData = byteArrayWithPopluatedHeader(PacketTypeAvatarData);
     avatarData.append(_myAvatar.toByteArray());
 
-    controlledBroadcastToNodes(avatarData, QSet() << NODE_TYPE_AVATAR_MIXER);
+    controlledBroadcastToNodes(avatarData, QSet() << NodeType::AvatarMixer);
 
     // Update _viewFrustum with latest camera and view frustum data...
     // NOTE: we get this from the view frustum, to make it simpler, since the
@@ -2374,11 +2374,11 @@ void Application::updateAvatar(float deltaTime) {
     loadViewFrustum(_myCamera, _viewFrustum);
 
     // Update my voxel servers with my current voxel query...
-    queryOctree(NODE_TYPE_VOXEL_SERVER, PacketTypeVoxelQuery, _voxelServerJurisdictions);
-    queryOctree(NODE_TYPE_PARTICLE_SERVER, PacketTypeParticleQuery, _particleServerJurisdictions);
+    queryOctree(NodeType::VoxelServer, PacketTypeVoxelQuery, _voxelServerJurisdictions);
+    queryOctree(NodeType::ParticleServer, PacketTypeParticleQuery, _particleServerJurisdictions);
 }
 
-void Application::queryOctree(NODE_TYPE serverType, PacketType packetType, NodeToJurisdictionMap& jurisdictions) {
+void Application::queryOctree(NodeType_t serverType, PacketType packetType, NodeToJurisdictionMap& jurisdictions) {
 
     // if voxels are disabled, then don't send this at all...
     if (!Menu::getInstance()->isOptionChecked(MenuOption::Voxels)) {
@@ -3192,8 +3192,8 @@ void Application::displayStats() {
         int pingAudio = 0, pingAvatar = 0, pingVoxel = 0, pingVoxelMax = 0;
 
         NodeList* nodeList = NodeList::getInstance();
-        SharedNodePointer audioMixerNode = nodeList->soloNodeOfType(NODE_TYPE_AUDIO_MIXER);
-        SharedNodePointer avatarMixerNode = nodeList->soloNodeOfType(NODE_TYPE_AVATAR_MIXER);
+        SharedNodePointer audioMixerNode = nodeList->soloNodeOfType(NodeType::AudioMixer);
+        SharedNodePointer avatarMixerNode = nodeList->soloNodeOfType(NodeType::AvatarMixer);
 
         pingAudio = audioMixerNode ? audioMixerNode->getPingMs() : 0;
         pingAvatar = avatarMixerNode ? avatarMixerNode->getPingMs() : 0;
@@ -3203,7 +3203,7 @@ void Application::displayStats() {
         int voxelServerCount = 0;
 
         foreach (const SharedNodePointer& node, nodeList->getNodeHash()) {
-            if (node->getType() == NODE_TYPE_VOXEL_SERVER) {
+            if (node->getType() == NodeType::VoxelServer) {
                 totalPingVoxel += node->getPingMs();
                 voxelServerCount++;
                 if (pingVoxelMax < node->getPingMs()) {
@@ -3274,7 +3274,7 @@ void Application::displayStats() {
     drawtext(horizontalOffset, verticalOffset, 0.10f, 0, 1.0, 2, avatarBodyYaw, .93f, .93f, .93f);
 
     if (_statsExpanded) {
-        SharedNodePointer avatarMixer = NodeList::getInstance()->soloNodeOfType(NODE_TYPE_AVATAR_MIXER);
+        SharedNodePointer avatarMixer = NodeList::getInstance()->soloNodeOfType(NodeType::AvatarMixer);
         if (avatarMixer) {
             sprintf(avatarMixerStats, "Avatar Mixer: %.f kbps, %.f pps",
                     roundf(avatarMixer->getAverageKilobitsPerSecond()),
@@ -3952,7 +3952,7 @@ void Application::domainChanged(const QString& domainHostname) {
 }
 
 void Application::nodeKilled(SharedNodePointer node) {
-    if (node->getType() == NODE_TYPE_VOXEL_SERVER) {
+    if (node->getType() == NodeType::VoxelServer) {
         QUuid nodeUUID = node->getUUID();
         // see if this is the first we've heard of this node...
         if (_voxelServerJurisdictions.find(nodeUUID) != _voxelServerJurisdictions.end()) {
@@ -3983,7 +3983,7 @@ void Application::nodeKilled(SharedNodePointer node) {
         }
         _voxelSceneStatsLock.unlock();
 
-    } else if (node->getType() == NODE_TYPE_PARTICLE_SERVER) {
+    } else if (node->getType() == NodeType::ParticleServer) {
         QUuid nodeUUID = node->getUUID();
         // see if this is the first we've heard of this node...
         if (_particleServerJurisdictions.find(nodeUUID) != _particleServerJurisdictions.end()) {
@@ -4014,7 +4014,7 @@ void Application::nodeKilled(SharedNodePointer node) {
         }
         _voxelSceneStatsLock.unlock();
 
-    } else if (node->getType() == NODE_TYPE_AVATAR_MIXER) {
+    } else if (node->getType() == NodeType::AvatarMixer) {
         // our avatar mixer has gone away - clear the hash of avatars
         _avatarManager.clearHash();
     }
@@ -4066,7 +4066,7 @@ int Application::parseOctreeStats(const QByteArray& packet, const HifiSockAddr&
 
         // see if this is the first we've heard of this node...
         NodeToJurisdictionMap* jurisdiction = NULL;
-        if (server->getType() == NODE_TYPE_VOXEL_SERVER) {
+        if (server->getType() == NodeType::VoxelServer) {
             jurisdiction = &_voxelServerJurisdictions;
         } else {
             jurisdiction = &_particleServerJurisdictions;
diff --git a/interface/src/Application.h b/interface/src/Application.h
index dae7d83da5..8daad301bf 100644
--- a/interface/src/Application.h
+++ b/interface/src/Application.h
@@ -175,7 +175,7 @@ public:
     Profile* getProfile() { return &_profile; }
     void resetProfile(const QString& username);
 
-    void controlledBroadcastToNodes(const QByteArray& packet, const QSet& destinationNodeTypes);
+    void controlledBroadcastToNodes(const QByteArray& packet, const QSet& destinationNodeTypes);
 
     void setupWorldLight();
 
@@ -298,7 +298,7 @@ private:
     void renderHighlightVoxel(VoxelDetail voxel);
 
     void updateAvatar(float deltaTime);
-    void queryOctree(NODE_TYPE serverType, PacketType packetType, NodeToJurisdictionMap& jurisdictions);
+    void queryOctree(NodeType_t serverType, PacketType packetType, NodeToJurisdictionMap& jurisdictions);
     void loadViewFrustum(Camera& camera, ViewFrustum& viewFrustum);
 
     glm::vec3 getSunDirection();
diff --git a/interface/src/Audio.cpp b/interface/src/Audio.cpp
index 752ba64910..e42947bf8c 100644
--- a/interface/src/Audio.cpp
+++ b/interface/src/Audio.cpp
@@ -365,7 +365,7 @@ void Audio::handleAudioInput() {
                             NETWORK_BUFFER_LENGTH_SAMPLES_PER_CHANNEL);
 
         NodeList* nodeList = NodeList::getInstance();
-        SharedNodePointer audioMixer = nodeList->soloNodeOfType(NODE_TYPE_AUDIO_MIXER);
+        SharedNodePointer audioMixer = nodeList->soloNodeOfType(NodeType::AudioMixer);
         
         if (audioMixer && nodeList->getNodeActiveSocketOrPing(audioMixer.data())) {
             MyAvatar* interfaceAvatar = Application::getInstance()->getAvatar();
diff --git a/interface/src/MetavoxelSystem.cpp b/interface/src/MetavoxelSystem.cpp
index 5bd83d969c..0196499a39 100644
--- a/interface/src/MetavoxelSystem.cpp
+++ b/interface/src/MetavoxelSystem.cpp
@@ -107,14 +107,14 @@ void MetavoxelSystem::render() {
 }
 
 void MetavoxelSystem::nodeAdded(SharedNodePointer node) {
-    if (node->getType() == NODE_TYPE_METAVOXEL_SERVER) {
+    if (node->getType() == NodeType::MetavoxelServer) {
         QMetaObject::invokeMethod(this, "addClient", Q_ARG(const QUuid&, node->getUUID()),
             Q_ARG(const HifiSockAddr&, node->getLocalSocket()));
     }
 }
 
 void MetavoxelSystem::nodeKilled(SharedNodePointer node) {
-    if (node->getType() == NODE_TYPE_METAVOXEL_SERVER) {
+    if (node->getType() == NodeType::MetavoxelServer) {
         QMetaObject::invokeMethod(this, "removeClient", Q_ARG(const QUuid&, node->getUUID()));
     }
 }
diff --git a/interface/src/ParticleTreeRenderer.h b/interface/src/ParticleTreeRenderer.h
index 20cb41b207..147456757c 100644
--- a/interface/src/ParticleTreeRenderer.h
+++ b/interface/src/ParticleTreeRenderer.h
@@ -28,7 +28,7 @@ public:
     virtual ~ParticleTreeRenderer();
 
     virtual Octree* createTree() { return new ParticleTree(true); }
-    virtual NODE_TYPE getMyNodeType() const { return NODE_TYPE_PARTICLE_SERVER; }
+    virtual NodeType_t getMyNodeType() const { return NodeType::ParticleServer; }
     virtual PacketType getMyQueryMessageType() const { return PacketTypeParticleQuery; }
     virtual PacketType getExpectedPacketType() const { return PacketTypeParticleData; }
     virtual void renderElement(OctreeElement* element, RenderArgs* args);
diff --git a/interface/src/VoxelSystem.cpp b/interface/src/VoxelSystem.cpp
index a663c27ce2..3297750fb9 100644
--- a/interface/src/VoxelSystem.cpp
+++ b/interface/src/VoxelSystem.cpp
@@ -1591,7 +1591,7 @@ void VoxelSystem::falseColorizeBySource() {
     // create a bunch of colors we'll use during colorization
 
     foreach (const SharedNodePointer& node, NodeList::getInstance()->getNodeHash()) {
-        if (node->getType() == NODE_TYPE_VOXEL_SERVER) {
+        if (node->getType() == NodeType::VoxelServer) {
             uint16_t nodeID = VoxelTreeElement::getSourceNodeUUIDKey(node->getUUID());
             int groupColor = voxelServerCount % NUMBER_OF_COLOR_GROUPS;
             args.colors[nodeID] = groupColors[groupColor];
@@ -2663,7 +2663,7 @@ void VoxelSystem::falseColorizeOccludedV2() {
 }
 
 void VoxelSystem::nodeAdded(SharedNodePointer node) {
-    if (node->getType() == NODE_TYPE_VOXEL_SERVER) {
+    if (node->getType() == NodeType::VoxelServer) {
         qDebug("VoxelSystem... voxel server %s added...", node->getUUID().toString().toLocal8Bit().constData());
         _voxelServerCount++;
     }
@@ -2684,7 +2684,7 @@ bool VoxelSystem::killSourceVoxelsOperation(OctreeElement* element, void* extraD
 }
 
 void VoxelSystem::nodeKilled(SharedNodePointer node) {
-    if (node->getType() == NODE_TYPE_VOXEL_SERVER) {
+    if (node->getType() == NodeType::VoxelServer) {
         _voxelServerCount--;
         QUuid nodeUUID = node->getUUID();
         qDebug("VoxelSystem... voxel server %s removed...", nodeUUID.toString().toLocal8Bit().constData());
diff --git a/interface/src/avatar/MyAvatar.cpp b/interface/src/avatar/MyAvatar.cpp
index cee524c171..e07c3b1715 100644
--- a/interface/src/avatar/MyAvatar.cpp
+++ b/interface/src/avatar/MyAvatar.cpp
@@ -473,7 +473,7 @@ void MyAvatar::loadData(QSettings* settings) {
 
 void MyAvatar::sendKillAvatar() {
     QByteArray killPacket = byteArrayWithPopluatedHeader(PacketTypeKillAvatar);
-    NodeList::getInstance()->broadcastToNodes(killPacket, QSet() << NODE_TYPE_AVATAR_MIXER);
+    NodeList::getInstance()->broadcastToNodes(killPacket, NodeSet() << NodeType::AvatarMixer);
 }
 
 void MyAvatar::orbit(const glm::vec3& position, int deltaX, int deltaY) {
diff --git a/interface/src/ui/VoxelStatsDialog.cpp b/interface/src/ui/VoxelStatsDialog.cpp
index 2c2702a21d..27b7f788ec 100644
--- a/interface/src/ui/VoxelStatsDialog.cpp
+++ b/interface/src/ui/VoxelStatsDialog.cpp
@@ -224,9 +224,9 @@ void VoxelStatsDialog::paintEvent(QPaintEvent* event) {
 void VoxelStatsDialog::showAllOctreeServers() {
     int serverCount = 0;
 
-    showOctreeServersOfType(serverCount, NODE_TYPE_VOXEL_SERVER, "Voxel", 
+    showOctreeServersOfType(serverCount, NodeType::VoxelServer, "Voxel",
             Application::getInstance()->getVoxelServerJurisdictions());
-    showOctreeServersOfType(serverCount, NODE_TYPE_PARTICLE_SERVER, "Particle", 
+    showOctreeServersOfType(serverCount, NodeType::ParticleServer, "Particle",
             Application::getInstance()->getParticleServerJurisdictions());
 
     if (_voxelServerLabelsCount > serverCount) {
@@ -239,7 +239,7 @@ void VoxelStatsDialog::showAllOctreeServers() {
     }
 }
 
-void VoxelStatsDialog::showOctreeServersOfType(int& serverCount, NODE_TYPE serverType, const char* serverTypeName,
+void VoxelStatsDialog::showOctreeServersOfType(int& serverCount, NodeType_t serverType, const char* serverTypeName,
                                                 NodeToJurisdictionMap& serverJurisdictions) {
                                                 
     QLocale locale(QLocale::English);
@@ -247,7 +247,7 @@ void VoxelStatsDialog::showOctreeServersOfType(int& serverCount, NODE_TYPE serve
     NodeList* nodeList = NodeList::getInstance();
 
     foreach (const SharedNodePointer& node, nodeList->getNodeHash()) {
-        // only send to the NodeTypes that are NODE_TYPE_VOXEL_SERVER
+        // only send to the NodeTypes that are NodeType_t_VOXEL_SERVER
         if (node->getType() == serverType) {
             serverCount++;
             
diff --git a/interface/src/ui/VoxelStatsDialog.h b/interface/src/ui/VoxelStatsDialog.h
index c1dcbdd734..f3a54241b5 100644
--- a/interface/src/ui/VoxelStatsDialog.h
+++ b/interface/src/ui/VoxelStatsDialog.h
@@ -44,7 +44,7 @@ protected:
     void RemoveStatItem(int item);
     void showAllOctreeServers();
 
-    void showOctreeServersOfType(int& serverNumber, NODE_TYPE serverType, 
+    void showOctreeServersOfType(int& serverNumber, NodeType_t serverType, 
                     const char* serverTypeName, NodeToJurisdictionMap& serverJurisdictions);
 
 private:
diff --git a/libraries/audio/src/AudioInjector.cpp b/libraries/audio/src/AudioInjector.cpp
index fd8bdc1a89..8bcf90784e 100644
--- a/libraries/audio/src/AudioInjector.cpp
+++ b/libraries/audio/src/AudioInjector.cpp
@@ -89,7 +89,7 @@ void AudioInjector::injectAudio() {
             memcpy(injectAudioPacket.data() + numPreAudioDataBytes, soundByteArray.data() + currentSendPosition, bytesToCopy);
             
             // grab our audio mixer from the NodeList, if it exists
-            SharedNodePointer audioMixer = nodeList->soloNodeOfType(NODE_TYPE_AUDIO_MIXER);
+            SharedNodePointer audioMixer = nodeList->soloNodeOfType(NodeType::AudioMixer);
             
             if (audioMixer && nodeList->getNodeActiveSocketOrPing(audioMixer.data())) {
                 // send off this audio packet
diff --git a/libraries/octree-server/src/OctreeServer.cpp b/libraries/octree-server/src/OctreeServer.cpp
index 9a4b0a51b3..73522565f9 100644
--- a/libraries/octree-server/src/OctreeServer.cpp
+++ b/libraries/octree-server/src/OctreeServer.cpp
@@ -469,7 +469,7 @@ void OctreeServer::processDatagram(const QByteArray& dataByteArray, const HifiSo
             qDebug() << "Got PacketType_VOXEL_QUERY at" << usecTimestampNow();
         }
        
-        // If we got a PacketType_VOXEL_QUERY, then we're talking to an NODE_TYPE_AVATAR, and we
+        // If we got a PacketType_VOXEL_QUERY, then we're talking to an NodeType_t_AVATAR, and we
         // need to make sure we have it in our nodeList.
         QUuid nodeUUID;
         deconstructPacketHeader(dataByteArray, nodeUUID);
@@ -552,7 +552,7 @@ void OctreeServer::run() {
     nodeList->setOwnerType(getMyNodeType());
 
     // we need to ask the DS about agents so we can ping/reply with them
-    nodeList->addNodeTypeToInterestSet(NODE_TYPE_AGENT);
+    nodeList->addNodeTypeToInterestSet(NodeType::Agent);
 
     setvbuf(stdout, NULL, _IOLBF, 0);
 
diff --git a/libraries/octree/src/JurisdictionListener.cpp b/libraries/octree/src/JurisdictionListener.cpp
index e28fb92cdb..fc8ea008d1 100644
--- a/libraries/octree/src/JurisdictionListener.cpp
+++ b/libraries/octree/src/JurisdictionListener.cpp
@@ -15,14 +15,14 @@
 #include 
 #include "JurisdictionListener.h"
 
-JurisdictionListener::JurisdictionListener(NODE_TYPE type) :
+JurisdictionListener::JurisdictionListener(NodeType_t type) :
     _packetSender(JurisdictionListener::DEFAULT_PACKETS_PER_SECOND)
 {
     _nodeType = type;
     ReceivedPacketProcessor::_dontSleep = true; // we handle sleeping so this class doesn't need to
     
     connect(NodeList::getInstance(), &NodeList::nodeKilled, this, &JurisdictionListener::nodeKilled);
-    //qDebug("JurisdictionListener::JurisdictionListener(NODE_TYPE type=%c)", type);
+    //qDebug("JurisdictionListener::JurisdictionListener(NodeType_t type=%c)", type);
     
     // tell our NodeList we want to hear about nodes with our node type
     NodeList::getInstance()->addNodeTypeToInterestSet(type);
diff --git a/libraries/octree/src/JurisdictionListener.h b/libraries/octree/src/JurisdictionListener.h
index d4cd396a48..712749aae7 100644
--- a/libraries/octree/src/JurisdictionListener.h
+++ b/libraries/octree/src/JurisdictionListener.h
@@ -28,15 +28,15 @@ public:
     static const int DEFAULT_PACKETS_PER_SECOND = 1;
     static const int NO_SERVER_CHECK_RATE = 60; // if no servers yet detected, keep checking at 60fps
 
-    JurisdictionListener(NODE_TYPE type = NODE_TYPE_VOXEL_SERVER);
+    JurisdictionListener(NodeType_t type = NodeType::VoxelServer);
     
     virtual bool process();
 
     NodeToJurisdictionMap* getJurisdictions() { return &_jurisdictions; };
 
 
-    NODE_TYPE getNodeType() const { return _nodeType; }
-    void setNodeType(NODE_TYPE type) { _nodeType = type; }
+    NodeType_t getNodeType() const { return _nodeType; }
+    void setNodeType(NodeType_t type) { _nodeType = type; }
 
 public slots:
     /// Called by NodeList to inform us that a node has been killed.
@@ -53,7 +53,7 @@ protected:
 
 private:
     NodeToJurisdictionMap _jurisdictions;
-    NODE_TYPE _nodeType;
+    NodeType_t _nodeType;
 
     bool queueJurisdictionRequest();
 
diff --git a/libraries/octree/src/JurisdictionMap.cpp b/libraries/octree/src/JurisdictionMap.cpp
index df980917e8..6dc5a22e73 100644
--- a/libraries/octree/src/JurisdictionMap.cpp
+++ b/libraries/octree/src/JurisdictionMap.cpp
@@ -92,7 +92,7 @@ void JurisdictionMap::clear() {
     _endNodes.clear();
 }
 
-JurisdictionMap::JurisdictionMap(NODE_TYPE type) : _rootOctalCode(NULL) {
+JurisdictionMap::JurisdictionMap(NodeType_t type) : _rootOctalCode(NULL) {
     _nodeType = type;
     unsigned char* rootCode = new unsigned char[1];
     *rootCode = 0;
@@ -262,7 +262,7 @@ bool JurisdictionMap::writeToFile(const char* filename) {
     return true;
 }
 
-int JurisdictionMap::packEmptyJurisdictionIntoMessage(NODE_TYPE type, unsigned char* destinationBuffer, int availableBytes) {
+int JurisdictionMap::packEmptyJurisdictionIntoMessage(NodeType_t type, unsigned char* destinationBuffer, int availableBytes) {
     unsigned char* bufferStart = destinationBuffer;
     
     int headerLength = populatePacketHeader(reinterpret_cast(destinationBuffer), PacketTypeJurisdiction);
@@ -287,7 +287,7 @@ int JurisdictionMap::packIntoMessage(unsigned char* destinationBuffer, int avail
     destinationBuffer += headerLength;
 
     // Pack the Node Type in first byte
-    NODE_TYPE type = getNodeType();
+    NodeType_t type = getNodeType();
     memcpy(destinationBuffer, &type, sizeof(type));
     destinationBuffer += sizeof(type);
 
diff --git a/libraries/octree/src/JurisdictionMap.h b/libraries/octree/src/JurisdictionMap.h
index 5380a0167a..219429712e 100644
--- a/libraries/octree/src/JurisdictionMap.h
+++ b/libraries/octree/src/JurisdictionMap.h
@@ -27,7 +27,7 @@ public:
     };
     
     // standard constructors
-    JurisdictionMap(NODE_TYPE type = NODE_TYPE_VOXEL_SERVER); // default constructor
+    JurisdictionMap(NodeType_t type = NodeType::VoxelServer); // default constructor
     JurisdictionMap(const JurisdictionMap& other); // copy constructor
 
     // standard assignment
@@ -60,12 +60,12 @@ public:
     int packIntoMessage(unsigned char* destinationBuffer, int availableBytes);
     
     /// Available to pack an empty or unknown jurisdiction into a network packet, used when no JurisdictionMap is available
-    static int packEmptyJurisdictionIntoMessage(NODE_TYPE type, unsigned char* destinationBuffer, int availableBytes);
+    static int packEmptyJurisdictionIntoMessage(NodeType_t type, unsigned char* destinationBuffer, int availableBytes);
 
     void displayDebugDetails() const;
     
-    NODE_TYPE getNodeType() const { return _nodeType; }
-    void setNodeType(NODE_TYPE type) { _nodeType = type; }
+    NodeType_t getNodeType() const { return _nodeType; }
+    void setNodeType(NodeType_t type) { _nodeType = type; }
     
 private:
     void copyContents(const JurisdictionMap& other); // use assignment instead
@@ -74,7 +74,7 @@ private:
 
     unsigned char* _rootOctalCode;
     std::vector _endNodes;
-    NODE_TYPE _nodeType;
+    NodeType_t _nodeType;
 };
 
 /// Map between node IDs and their reported JurisdictionMap. Typically used by classes that need to know which nodes are 
diff --git a/libraries/octree/src/JurisdictionSender.cpp b/libraries/octree/src/JurisdictionSender.cpp
index f3ee5def2e..52990397db 100644
--- a/libraries/octree/src/JurisdictionSender.cpp
+++ b/libraries/octree/src/JurisdictionSender.cpp
@@ -16,7 +16,7 @@
 #include "JurisdictionSender.h"
 
 
-JurisdictionSender::JurisdictionSender(JurisdictionMap* map, NODE_TYPE type) :
+JurisdictionSender::JurisdictionSender(JurisdictionMap* map, NodeType_t type) :
     ReceivedPacketProcessor(),
     _jurisdictionMap(map),
     _packetSender(JurisdictionSender::DEFAULT_PACKETS_PER_SECOND)
diff --git a/libraries/octree/src/JurisdictionSender.h b/libraries/octree/src/JurisdictionSender.h
index 7c8f288728..19ce727a57 100644
--- a/libraries/octree/src/JurisdictionSender.h
+++ b/libraries/octree/src/JurisdictionSender.h
@@ -26,15 +26,15 @@ class JurisdictionSender : public ReceivedPacketProcessor {
 public:
     static const int DEFAULT_PACKETS_PER_SECOND = 1;
 
-    JurisdictionSender(JurisdictionMap* map, NODE_TYPE type = NODE_TYPE_VOXEL_SERVER);
+    JurisdictionSender(JurisdictionMap* map, NodeType_t type = NodeType::VoxelServer);
     ~JurisdictionSender();
 
     void setJurisdiction(JurisdictionMap* map) { _jurisdictionMap = map; }
 
     virtual bool process();
 
-    NODE_TYPE getNodeType() const { return _nodeType; }
-    void setNodeType(NODE_TYPE type) { _nodeType = type; }
+    NodeType_t getNodeType() const { return _nodeType; }
+    void setNodeType(NodeType_t type) { _nodeType = type; }
 
 protected:
     virtual void processPacket(const HifiSockAddr& senderAddress, const QByteArray& packet);
@@ -50,7 +50,7 @@ private:
     QMutex _requestingNodeMutex;
     JurisdictionMap* _jurisdictionMap;
     std::queue _nodesRequestingJurisdictions;
-    NODE_TYPE _nodeType;
+    NodeType_t _nodeType;
     
     PacketSender _packetSender;
 };
diff --git a/libraries/octree/src/OctreeRenderer.h b/libraries/octree/src/OctreeRenderer.h
index c1d3e85aef..b65e2889e6 100644
--- a/libraries/octree/src/OctreeRenderer.h
+++ b/libraries/octree/src/OctreeRenderer.h
@@ -37,7 +37,7 @@ public:
     virtual ~OctreeRenderer();
 
     virtual Octree* createTree() = 0;
-    virtual NODE_TYPE getMyNodeType() const = 0;
+    virtual NodeType_t getMyNodeType() const = 0;
     virtual PacketType getMyQueryMessageType() const = 0;
     virtual PacketType getExpectedPacketType() const = 0;
     virtual void renderElement(OctreeElement* element, RenderArgs* args) = 0;
diff --git a/libraries/octree/src/OctreeScriptingInterface.h b/libraries/octree/src/OctreeScriptingInterface.h
index 1158f21438..34eddd8bed 100644
--- a/libraries/octree/src/OctreeScriptingInterface.h
+++ b/libraries/octree/src/OctreeScriptingInterface.h
@@ -29,7 +29,7 @@ public:
     void setJurisdictionListener(JurisdictionListener* jurisdictionListener);
     void init();
     
-    virtual NODE_TYPE getServerNodeType() const = 0;
+    virtual NodeType_t getServerNodeType() const = 0;
     virtual OctreeEditPacketSender* createPacketSender() = 0;
 
 public slots:
diff --git a/libraries/particle-server/src/ParticleServer.h b/libraries/particle-server/src/ParticleServer.h
index 4420edf947..1c1e3b5be9 100644
--- a/libraries/particle-server/src/ParticleServer.h
+++ b/libraries/particle-server/src/ParticleServer.h
@@ -26,7 +26,7 @@ public:
     // Subclasses must implement these methods
     virtual OctreeQueryNode* createOctreeQueryNode();
     virtual Octree* createTree();
-    virtual unsigned char getMyNodeType() const { return NODE_TYPE_PARTICLE_SERVER; }
+    virtual unsigned char getMyNodeType() const { return NodeType::ParticleServer; }
     virtual PacketType getMyQueryMessageType() const { return PacketTypeParticleQuery; }
     virtual const char* getMyServerName() const { return PARTICLE_SERVER_NAME; }
     virtual const char* getMyLoggingServerTargetName() const { return PARTICLE_SERVER_LOGGING_TARGET_NAME; }
diff --git a/libraries/particles/src/ParticleCollisionSystem.cpp b/libraries/particles/src/ParticleCollisionSystem.cpp
index e9484e99d9..d06d13795b 100644
--- a/libraries/particles/src/ParticleCollisionSystem.cpp
+++ b/libraries/particles/src/ParticleCollisionSystem.cpp
@@ -193,7 +193,7 @@ void ParticleCollisionSystem::updateCollisionWithAvatars(Particle* particle) {
     // loop through all the other avatars for potential interactions...
 //    foreach (const SharedNodePointer& node, NodeList::getInstance()->getNodeHash()) {
 //        //qDebug() << "updateCollisionWithAvatars()... node:" << *node << "\n";
-//        if (node->getLinkedData() && node->getType() == NODE_TYPE_AGENT) {
+//        if (node->getLinkedData() && node->getType() == NodeType_t_AGENT) {
 //            AvatarData* avatar = static_cast(node->getLinkedData());
 //            CollisionInfo collisionInfo;
 //            if (avatar->findSphereCollision(center, radius, collisionInfo)) {
diff --git a/libraries/particles/src/ParticleEditPacketSender.h b/libraries/particles/src/ParticleEditPacketSender.h
index f406ba625a..3169c5629d 100644
--- a/libraries/particles/src/ParticleEditPacketSender.h
+++ b/libraries/particles/src/ParticleEditPacketSender.h
@@ -29,7 +29,7 @@ public:
     void queueParticleEditMessage(PacketType type, ParticleID particleID, const ParticleProperties& properties);
 
     // My server type is the particle server
-    virtual unsigned char getMyNodeType() const { return NODE_TYPE_PARTICLE_SERVER; }
+    virtual unsigned char getMyNodeType() const { return NodeType::ParticleServer; }
     virtual void adjustEditPacketForClockSkew(unsigned char* codeColorBuffer, ssize_t length, int clockSkew);
 };
 #endif // __shared__ParticleEditPacketSender__
diff --git a/libraries/particles/src/ParticlesScriptingInterface.h b/libraries/particles/src/ParticlesScriptingInterface.h
index a85997ee05..dc5793ae30 100644
--- a/libraries/particles/src/ParticlesScriptingInterface.h
+++ b/libraries/particles/src/ParticlesScriptingInterface.h
@@ -21,7 +21,7 @@ public:
     ParticlesScriptingInterface();
     
     ParticleEditPacketSender* getParticlePacketSender() const { return (ParticleEditPacketSender*)getPacketSender(); }
-    virtual NODE_TYPE getServerNodeType() const { return NODE_TYPE_PARTICLE_SERVER; }
+    virtual NodeType_t getServerNodeType() const { return NodeType::ParticleServer; }
     virtual OctreeEditPacketSender* createPacketSender() { return new ParticleEditPacketSender(); }
 
     void setParticleTree(ParticleTree* particleTree) { _particleTree = particleTree; }
diff --git a/libraries/script-engine/src/ScriptEngine.cpp b/libraries/script-engine/src/ScriptEngine.cpp
index 937162e0bf..d16ddcd56d 100644
--- a/libraries/script-engine/src/ScriptEngine.cpp
+++ b/libraries/script-engine/src/ScriptEngine.cpp
@@ -249,7 +249,7 @@ void ScriptEngine::run() {
             avatarPacket.resize(numAvatarHeaderBytes);
             avatarPacket.append(_avatarData->toByteArray());
             
-            nodeList->broadcastToNodes(avatarPacket, QSet() << NODE_TYPE_AVATAR_MIXER);
+            nodeList->broadcastToNodes(avatarPacket, NodeSet() << NodeType::AvatarMixer);
         }
 
         if (willSendVisualDataCallBack) {
diff --git a/libraries/shared/src/Assignment.cpp b/libraries/shared/src/Assignment.cpp
index 5432278b17..2bff4ddcd0 100644
--- a/libraries/shared/src/Assignment.cpp
+++ b/libraries/shared/src/Assignment.cpp
@@ -17,19 +17,19 @@
 const char IPv4_ADDRESS_DESIGNATOR = 4;
 const char IPv6_ADDRESS_DESIGNATOR = 6;
 
-Assignment::Type Assignment::typeForNodeType(NODE_TYPE nodeType) {
+Assignment::Type Assignment::typeForNodeType(NodeType_t nodeType) {
     switch (nodeType) {
-        case NODE_TYPE_AUDIO_MIXER:
+        case NodeType::AudioMixer:
             return Assignment::AudioMixerType;
-        case NODE_TYPE_AVATAR_MIXER:
+        case NodeType::AvatarMixer:
             return Assignment::AvatarMixerType;
-        case NODE_TYPE_AGENT:
+        case NodeType::Agent:
             return Assignment::AgentType;
-        case NODE_TYPE_VOXEL_SERVER:
+        case NodeType::VoxelServer:
             return Assignment::VoxelServerType;
-        case NODE_TYPE_PARTICLE_SERVER:
+        case NodeType::ParticleServer:
             return Assignment::ParticleServerType;
-        case NODE_TYPE_METAVOXEL_SERVER:
+        case NodeType::MetavoxelServer:
             return Assignment::MetavoxelServerType;
         default:
             return Assignment::AllTypes;
diff --git a/libraries/shared/src/Assignment.h b/libraries/shared/src/Assignment.h
index 2cf026682a..418ea7fe09 100644
--- a/libraries/shared/src/Assignment.h
+++ b/libraries/shared/src/Assignment.h
@@ -50,7 +50,7 @@ public:
         LocalLocation
     };
 
-    static Assignment::Type typeForNodeType(NODE_TYPE nodeType);
+    static Assignment::Type typeForNodeType(NodeType_t nodeType);
 
     Assignment();
     Assignment(Assignment::Command command,
diff --git a/libraries/shared/src/Node.cpp b/libraries/shared/src/Node.cpp
index 18367019ad..adcb7357bf 100644
--- a/libraries/shared/src/Node.cpp
+++ b/libraries/shared/src/Node.cpp
@@ -20,6 +20,29 @@
 
 #include 
 
+const QString UNKNOWN_NodeType_t_NAME = "Unknown";
+
+namespace NodeType {
+    QHash TypeNameHash;
+}
+
+void NodeType::init() {
+    TypeNameHash.insert(NodeType::DomainServer, "Domain Server");
+    TypeNameHash.insert(NodeType::VoxelServer, "Voxel Server");
+    TypeNameHash.insert(NodeType::ParticleServer, "Particle Server");
+    TypeNameHash.insert(NodeType::MetavoxelServer, "Metavoxel Server");
+    TypeNameHash.insert(NodeType::Agent, "Agent");
+    TypeNameHash.insert(NodeType::AudioMixer, "Audio Mixer");
+    TypeNameHash.insert(NodeType::AvatarMixer, "Avatar Mixer");
+    TypeNameHash.insert(NodeType::AnimationServer, "Animation Server");
+    TypeNameHash.insert(NodeType::Unassigned, "Unassigned");
+}
+
+const QString& NodeType::getNodeTypeName(NodeType_t nodeType) {
+    QHash::iterator matchedTypeName = TypeNameHash.find(nodeType);
+    return matchedTypeName != TypeNameHash.end() ? matchedTypeName.value() : UNKNOWN_NodeType_t_NAME;
+}
+
 Node::Node(const QUuid& uuid, char type, const HifiSockAddr& publicSocket, const HifiSockAddr& localSocket) :
     _type(type),
     _uuid(uuid),
@@ -44,44 +67,6 @@ Node::~Node() {
     delete _bytesReceivedMovingAverage;
 }
 
-// Names of Node Types
-const char* NODE_TYPE_NAME_DOMAIN = "Domain";
-const char* NODE_TYPE_NAME_VOXEL_SERVER = "Voxel Server";
-const char* NODE_TYPE_NAME_PARTICLE_SERVER = "Particle Server";
-const char* NODE_TYPE_NAME_METAVOXEL_SERVER = "Metavoxel Server";
-const char* NODE_TYPE_NAME_AGENT = "Agent";
-const char* NODE_TYPE_NAME_AUDIO_MIXER = "Audio Mixer";
-const char* NODE_TYPE_NAME_AVATAR_MIXER = "Avatar Mixer";
-const char* NODE_TYPE_NAME_AUDIO_INJECTOR = "Audio Injector";
-const char* NODE_TYPE_NAME_ANIMATION_SERVER = "Animation Server";
-const char* NODE_TYPE_NAME_UNASSIGNED = "Unassigned";
-const char* NODE_TYPE_NAME_UNKNOWN = "Unknown";
-
-const char* Node::getTypeName() const {
-	switch (this->_type) {
-		case NODE_TYPE_DOMAIN:
-			return NODE_TYPE_NAME_DOMAIN;
-		case NODE_TYPE_VOXEL_SERVER:
-			return NODE_TYPE_NAME_VOXEL_SERVER;
-		case NODE_TYPE_PARTICLE_SERVER:
-		    return NODE_TYPE_NAME_PARTICLE_SERVER;
-		case NODE_TYPE_METAVOXEL_SERVER:
-		    return NODE_TYPE_NAME_METAVOXEL_SERVER;
-		case NODE_TYPE_AGENT:
-			return NODE_TYPE_NAME_AGENT;
-		case NODE_TYPE_AUDIO_MIXER:
-			return NODE_TYPE_NAME_AUDIO_MIXER;
-        case NODE_TYPE_AVATAR_MIXER:
-            return NODE_TYPE_NAME_AVATAR_MIXER;
-        case NODE_TYPE_ANIMATION_SERVER:
-            return NODE_TYPE_NAME_ANIMATION_SERVER;
-        case NODE_TYPE_UNASSIGNED:
-            return NODE_TYPE_NAME_UNASSIGNED;
-        default:
-            return NODE_TYPE_NAME_UNKNOWN;
-	}
-}
-
 void Node::setPublicSocket(const HifiSockAddr& publicSocket) {
     if (_activeSocket == &_publicSocket) {
         // if the active socket was the public socket then reset it to NULL
@@ -153,7 +138,7 @@ QDataStream& operator>>(QDataStream& in, Node& node) {
 }
 
 QDebug operator<<(QDebug debug, const Node &node) {
-    debug.nospace() << node.getTypeName() << " (" << node.getType() << ")";
+    debug.nospace() << NodeType::getNodeTypeName(node.getType()) << " (" << node.getType() << ")";
     debug << " " << node.getUUID().toString().toLocal8Bit().constData() << " ";
     debug.nospace() << node.getPublicSocket() << "/" << node.getLocalSocket();
     return debug.nospace();
diff --git a/libraries/shared/src/Node.h b/libraries/shared/src/Node.h
index 60d14a9dd3..952e1b1be2 100644
--- a/libraries/shared/src/Node.h
+++ b/libraries/shared/src/Node.h
@@ -27,17 +27,23 @@
 #include "NodeData.h"
 #include "SimpleMovingAverage.h"
 
-typedef quint8 NODE_TYPE;
-const NODE_TYPE NODE_TYPE_DOMAIN = 'D';
-const NODE_TYPE NODE_TYPE_VOXEL_SERVER = 'V';
-const NODE_TYPE NODE_TYPE_PARTICLE_SERVER = 'P';
-const NODE_TYPE NODE_TYPE_METAVOXEL_SERVER = 'm';
-const NODE_TYPE NODE_TYPE_ENVIRONMENT_SERVER = 'E';
-const NODE_TYPE NODE_TYPE_AGENT = 'I';
-const NODE_TYPE NODE_TYPE_AUDIO_MIXER = 'M';
-const NODE_TYPE NODE_TYPE_AVATAR_MIXER = 'W';
-const NODE_TYPE NODE_TYPE_ANIMATION_SERVER = 'a';
-const NODE_TYPE NODE_TYPE_UNASSIGNED = 1;
+typedef quint8 NodeType_t;
+
+namespace NodeType {
+    const NodeType_t DomainServer = 'D';
+    const NodeType_t VoxelServer = 'V';
+    const NodeType_t ParticleServer = 'P';
+    const NodeType_t MetavoxelServer = 'm';
+    const NodeType_t EnvironmentServer = 'E';
+    const NodeType_t Agent = 'I';
+    const NodeType_t AudioMixer = 'M';
+    const NodeType_t AvatarMixer = 'W';
+    const NodeType_t AnimationServer = 'a';
+    const NodeType_t Unassigned = 1;
+    
+    void init();
+    const QString& getNodeTypeName(NodeType_t nodeType);
+}
 
 class Node : public QObject {
     Q_OBJECT
@@ -50,7 +56,7 @@ public:
 
     char getType() const { return _type; }
     void setType(char type) { _type = type; }
-    const char* getTypeName() const;
+    
 
     const QUuid& getUUID() const { return _uuid; }
     void setUUID(const QUuid& uuid) { _uuid = uuid; }
@@ -96,7 +102,7 @@ private:
     Node(const Node &otherNode);
     Node& operator=(Node otherNode);
 
-    NODE_TYPE _type;
+    NodeType_t _type;
     QUuid _uuid;
     quint64 _wakeMicrostamp;
     quint64 _lastHeardMicrostamp;
diff --git a/libraries/shared/src/NodeList.cpp b/libraries/shared/src/NodeList.cpp
index e26185b8ef..aedfef9a3d 100644
--- a/libraries/shared/src/NodeList.cpp
+++ b/libraries/shared/src/NodeList.cpp
@@ -22,8 +22,8 @@
 #include "UUID.h"
 
 const char SOLO_NODE_TYPES[2] = {
-    NODE_TYPE_AVATAR_MIXER,
-    NODE_TYPE_AUDIO_MIXER
+    NodeType::AvatarMixer,
+    NodeType::AudioMixer
 };
 
 const QString DEFAULT_DOMAIN_HOSTNAME = "alpha.highfidelity.io";
@@ -33,6 +33,8 @@ NodeList* NodeList::_sharedInstance = NULL;
 
 NodeList* NodeList::createInstance(char ownerType, unsigned short int socketListenPort) {
     if (!_sharedInstance) {
+        NodeType::init();
+        
         _sharedInstance = new NodeList(ownerType, socketListenPort);
 
         // register the SharedNodePointer meta-type for signals/slots
@@ -257,11 +259,11 @@ void NodeList::reset() {
     _ownerUUID = QUuid::createUuid();
 }
 
-void NodeList::addNodeTypeToInterestSet(NODE_TYPE nodeTypeToAdd) {
+void NodeList::addNodeTypeToInterestSet(NodeType_t nodeTypeToAdd) {
     _nodeTypesOfInterest << nodeTypeToAdd;
 }
 
-void NodeList::addSetOfNodeTypesToNodeInterestSet(const QSet& setOfNodeTypes) {
+void NodeList::addSetOfNodeTypesToNodeInterestSet(const QSet& setOfNodeTypes) {
     _nodeTypesOfInterest.unite(setOfNodeTypes);
 }
 
@@ -471,7 +473,7 @@ void NodeList::sendDomainServerCheckIn() {
             << (quint8) _nodeTypesOfInterest.size();
         
         // copy over the bytes for node types of interest, if required
-        foreach (NODE_TYPE nodeTypeOfInterest, _nodeTypesOfInterest) {
+        foreach (NodeType_t nodeTypeOfInterest, _nodeTypesOfInterest) {
             packetStream << nodeTypeOfInterest;
         }
         
@@ -595,9 +597,9 @@ SharedNodePointer NodeList::addOrUpdateNode(const QUuid& uuid, char nodeType,
         
         QMutexLocker locker(&matchingNode->getMutex());
 
-        if (matchingNode->getType() == NODE_TYPE_AUDIO_MIXER ||
-            matchingNode->getType() == NODE_TYPE_VOXEL_SERVER ||
-            matchingNode->getType() == NODE_TYPE_METAVOXEL_SERVER) {
+        if (matchingNode->getType() == NodeType::AudioMixer ||
+            matchingNode->getType() == NodeType::VoxelServer ||
+            matchingNode->getType() == NodeType::MetavoxelServer) {
             // until the Audio class also uses our nodeList, we need to update
             // the lastRecvTimeUsecs for the audio mixer so it doesn't get killed and re-added continously
             matchingNode->setLastHeardMicrostamp(usecTimestampNow());
@@ -619,7 +621,7 @@ SharedNodePointer NodeList::addOrUpdateNode(const QUuid& uuid, char nodeType,
 }
 
 unsigned NodeList::broadcastToNodes(const QByteArray& packet,
-                                    const QSet& destinationNodeTypes) {
+                                    const QSet& destinationNodeTypes) {
     unsigned n = 0;
 
     foreach (const SharedNodePointer& node, getNodeHash()) {
diff --git a/libraries/shared/src/NodeList.h b/libraries/shared/src/NodeList.h
index 69c7303c7b..b3ac019a42 100644
--- a/libraries/shared/src/NodeList.h
+++ b/libraries/shared/src/NodeList.h
@@ -30,9 +30,6 @@
 
 #include "Node.h"
 
-const int MAX_NUM_NODES = 10000;
-const int NODES_PER_BUCKET = 100;
-
 const int MAX_PACKET_SIZE = 1500;
 
 const quint64 NODE_SILENCE_THRESHOLD_USECS = 2 * 1000 * 1000;
@@ -53,6 +50,8 @@ const int MAX_SILENT_DOMAIN_SERVER_CHECK_INS = 5;
 class Assignment;
 class HifiSockAddr;
 
+typedef QSet NodeSet;
+
 typedef QSharedPointer SharedNodePointer;
 typedef QHash NodeHash;
 Q_DECLARE_METATYPE(SharedNodePointer)
@@ -62,8 +61,8 @@ class NodeList : public QObject {
 public:
     static NodeList* createInstance(char ownerType, unsigned short int socketListenPort = 0);
     static NodeList* getInstance();
-    NODE_TYPE getOwnerType() const { return _ownerType; }
-    void setOwnerType(NODE_TYPE ownerType) { _ownerType = ownerType; }
+    NodeType_t getOwnerType() const { return _ownerType; }
+    void setOwnerType(NodeType_t ownerType) { _ownerType = ownerType; }
 
     const QString& getDomainHostname() const { return _domainHostname; }
     void setDomainHostname(const QString& domainHostname);
@@ -89,9 +88,9 @@ public:
 
     void reset();
     
-    const QSet& getNodeInterestSet() const { return _nodeTypesOfInterest; }
-    void addNodeTypeToInterestSet(NODE_TYPE nodeTypeToAdd);
-    void addSetOfNodeTypesToNodeInterestSet(const QSet& setOfNodeTypes);
+    const NodeSet& getNodeInterestSet() const { return _nodeTypesOfInterest; }
+    void addNodeTypeToInterestSet(NodeType_t nodeTypeToAdd);
+    void addSetOfNodeTypesToNodeInterestSet(const NodeSet& setOfNodeTypes);
 
     int processDomainServerList(const QByteArray& packet);
 
@@ -112,7 +111,7 @@ public:
 
     int updateNodeWithData(Node *node, const HifiSockAddr& senderSockAddr, const QByteArray& packet);
 
-    unsigned broadcastToNodes(const QByteArray& packet, const QSet& destinationNodeTypes);
+    unsigned broadcastToNodes(const QByteArray& packet, const NodeSet& destinationNodeTypes);
     SharedNodePointer soloNodeOfType(char nodeType);
 
     void loadData(QSettings* settings);
@@ -146,8 +145,8 @@ private:
     QString _domainHostname;
     HifiSockAddr _domainSockAddr;
     QUdpSocket _nodeSocket;
-    NODE_TYPE _ownerType;
-    QSet _nodeTypesOfInterest;
+    NodeType_t _ownerType;
+    NodeSet _nodeTypesOfInterest;
     QUuid _ownerUUID;
     int _numNoReplyDomainCheckIns;
     HifiSockAddr _assignmentServerSocket;
diff --git a/libraries/shared/src/ThreadedAssignment.cpp b/libraries/shared/src/ThreadedAssignment.cpp
index 148f06ec85..2c1110491b 100644
--- a/libraries/shared/src/ThreadedAssignment.cpp
+++ b/libraries/shared/src/ThreadedAssignment.cpp
@@ -33,7 +33,7 @@ void ThreadedAssignment::setFinished(bool isFinished) {
     }
 }
 
-void ThreadedAssignment::commonInit(const char* targetName, NODE_TYPE nodeType) {
+void ThreadedAssignment::commonInit(const char* targetName, NodeType_t nodeType) {
     // change the logging target name while the assignment is running
     Logging::setTargetName(targetName);
     
diff --git a/libraries/shared/src/ThreadedAssignment.h b/libraries/shared/src/ThreadedAssignment.h
index 1f59aa4623..7c7aa9a63e 100644
--- a/libraries/shared/src/ThreadedAssignment.h
+++ b/libraries/shared/src/ThreadedAssignment.h
@@ -25,7 +25,7 @@ public slots:
     
     virtual void processDatagram(const QByteArray& dataByteArray, const HifiSockAddr& senderSockAddr) = 0;
 protected:
-    void commonInit(const char* targetName, NODE_TYPE nodeType);
+    void commonInit(const char* targetName, NodeType_t nodeType);
     bool _isFinished;
 private slots:
     void checkInWithDomainServerOrExit();
diff --git a/libraries/voxel-server/src/VoxelServer.cpp b/libraries/voxel-server/src/VoxelServer.cpp
index 481a6c436b..b71bcd3dc2 100644
--- a/libraries/voxel-server/src/VoxelServer.cpp
+++ b/libraries/voxel-server/src/VoxelServer.cpp
@@ -69,5 +69,5 @@ void VoxelServer::beforeRun() {
     }
     qDebug("Sending environments=%s", debug::valueOf(_sendEnvironments));
     
-    NodeList::getInstance()->addNodeTypeToInterestSet(NODE_TYPE_ANIMATION_SERVER);
+    NodeList::getInstance()->addNodeTypeToInterestSet(NodeType::AnimationServer);
 }
diff --git a/libraries/voxel-server/src/VoxelServer.h b/libraries/voxel-server/src/VoxelServer.h
index 9e4a1d23df..183224b2a7 100644
--- a/libraries/voxel-server/src/VoxelServer.h
+++ b/libraries/voxel-server/src/VoxelServer.h
@@ -36,7 +36,7 @@ public:
     // Subclasses must implement these methods
     virtual OctreeQueryNode* createOctreeQueryNode();
     virtual Octree* createTree();
-    virtual unsigned char getMyNodeType() const { return NODE_TYPE_VOXEL_SERVER; }
+    virtual unsigned char getMyNodeType() const { return NodeType::VoxelServer; }
     virtual PacketType getMyQueryMessageType() const { return PacketTypeVoxelQuery; }
     virtual const char* getMyServerName() const { return VOXEL_SERVER_NAME; }
     virtual const char* getMyLoggingServerTargetName() const { return VOXEL_SERVER_LOGGING_TARGET_NAME; }
diff --git a/libraries/voxels/src/VoxelEditPacketSender.h b/libraries/voxels/src/VoxelEditPacketSender.h
index d99c176d92..79d9f8c757 100644
--- a/libraries/voxels/src/VoxelEditPacketSender.h
+++ b/libraries/voxels/src/VoxelEditPacketSender.h
@@ -44,6 +44,6 @@ public:
     bool voxelServersExist() const { return serversExist(); }
 
     // My server type is the voxel server
-    virtual unsigned char getMyNodeType() const { return NODE_TYPE_VOXEL_SERVER; }
+    virtual unsigned char getMyNodeType() const { return NodeType::VoxelServer; }
 };
 #endif // __shared__VoxelEditPacketSender__
diff --git a/libraries/voxels/src/VoxelsScriptingInterface.h b/libraries/voxels/src/VoxelsScriptingInterface.h
index bef3b9782e..dc53840cb1 100644
--- a/libraries/voxels/src/VoxelsScriptingInterface.h
+++ b/libraries/voxels/src/VoxelsScriptingInterface.h
@@ -22,7 +22,7 @@ class VoxelsScriptingInterface : public OctreeScriptingInterface {
 public:    
     VoxelEditPacketSender* getVoxelPacketSender() { return (VoxelEditPacketSender*)getPacketSender(); }
 
-    virtual NODE_TYPE getServerNodeType() const { return NODE_TYPE_VOXEL_SERVER; }
+    virtual NodeType_t getServerNodeType() const { return NodeType::VoxelServer; }
     virtual OctreeEditPacketSender* createPacketSender() { return new VoxelEditPacketSender(); }
 
 public slots:

From 423e1598f076541585eb3f265c7dbba4849a1df9 Mon Sep 17 00:00:00 2001
From: Stephen Birarda 
Date: Tue, 28 Jan 2014 13:41:39 -0800
Subject: [PATCH 13/16] use NodeSet in place of QSet where possible

---
 domain-server/src/DomainServer.cpp |  2 +-
 interface/src/Application.cpp      | 11 +++++------
 interface/src/Application.h        |  2 +-
 libraries/shared/src/NodeList.cpp  |  4 ++--
 4 files changed, 9 insertions(+), 10 deletions(-)

diff --git a/domain-server/src/DomainServer.cpp b/domain-server/src/DomainServer.cpp
index c861e678a0..6e4a4cdff4 100644
--- a/domain-server/src/DomainServer.cpp
+++ b/domain-server/src/DomainServer.cpp
@@ -144,7 +144,7 @@ void DomainServer::readAvailableDatagrams() {
                     }
                 }
                 
-                const QSet STATICALLY_ASSIGNED_NODES = QSet() << NodeType::AudioMixer
+                const NodeSet STATICALLY_ASSIGNED_NODES = NodeSet() << NodeType::AudioMixer
                     << NodeType::AvatarMixer << NodeType::VoxelServer << NodeType::ParticleServer
                     << NodeType::MetavoxelServer;
                 
diff --git a/interface/src/Application.cpp b/interface/src/Application.cpp
index eccf2dae10..62ca9a2af4 100644
--- a/interface/src/Application.cpp
+++ b/interface/src/Application.cpp
@@ -229,7 +229,7 @@ Application::Application(int& argc, char** argv, timeval &startup_time) :
     #endif
 
     // tell the NodeList instance who to tell the domain server we care about
-    nodeList->addSetOfNodeTypesToNodeInterestSet(QSet() << NodeType::AudioMixer << NodeType::AvatarMixer
+    nodeList->addSetOfNodeTypesToNodeInterestSet(NodeSet() << NodeType::AudioMixer << NodeType::AvatarMixer
                                                  << NodeType::VoxelServer << NodeType::ParticleServer
                                                  << NodeType::MetavoxelServer);
     
@@ -648,8 +648,7 @@ void Application::resetProfile(const QString& username) {
     updateWindowTitle();
 }
 
-void Application::controlledBroadcastToNodes(const QByteArray& packet,
-                                             const QSet& destinationNodeTypes) {
+void Application::controlledBroadcastToNodes(const QByteArray& packet, const NodeSet& destinationNodeTypes) {
     foreach(NodeType_t type, destinationNodeTypes) {
         // Intercept data to voxel server when voxels are disabled
         if (type == NodeType::VoxelServer && !Menu::getInstance()->isOptionChecked(MenuOption::Voxels)) {
@@ -657,7 +656,7 @@ void Application::controlledBroadcastToNodes(const QByteArray& packet,
         }
         
         // Perform the broadcast for one type
-        int nReceivingNodes = NodeList::getInstance()->broadcastToNodes(packet, QSet() << type);
+        int nReceivingNodes = NodeList::getInstance()->broadcastToNodes(packet, NodeSet() << type);
         
         // Feed number of bytes to corresponding channel of the bandwidth meter, if any (done otherwise)
         BandwidthMeter::ChannelIndex channel;
@@ -1332,7 +1331,7 @@ void Application::wheelEvent(QWheelEvent* event) {
 
 void Application::sendPingPackets() {
     QByteArray pingPacket = NodeList::getInstance()->constructPingPacket();
-    getInstance()->controlledBroadcastToNodes(pingPacket, QSet() << NodeType::VoxelServer
+    getInstance()->controlledBroadcastToNodes(pingPacket, NodeSet() << NodeType::VoxelServer
                                               << NodeType::ParticleServer
                                               << NodeType::AudioMixer << NodeType::AvatarMixer
                                               << NodeType::MetavoxelServer);
@@ -2363,7 +2362,7 @@ void Application::updateAvatar(float deltaTime) {
     QByteArray avatarData = byteArrayWithPopluatedHeader(PacketTypeAvatarData);
     avatarData.append(_myAvatar.toByteArray());
 
-    controlledBroadcastToNodes(avatarData, QSet() << NodeType::AvatarMixer);
+    controlledBroadcastToNodes(avatarData, NodeSet() << NodeType::AvatarMixer);
 
     // Update _viewFrustum with latest camera and view frustum data...
     // NOTE: we get this from the view frustum, to make it simpler, since the
diff --git a/interface/src/Application.h b/interface/src/Application.h
index 8daad301bf..d38c3675d7 100644
--- a/interface/src/Application.h
+++ b/interface/src/Application.h
@@ -175,7 +175,7 @@ public:
     Profile* getProfile() { return &_profile; }
     void resetProfile(const QString& username);
 
-    void controlledBroadcastToNodes(const QByteArray& packet, const QSet& destinationNodeTypes);
+    void controlledBroadcastToNodes(const QByteArray& packet, const NodeSet& destinationNodeTypes);
 
     void setupWorldLight();
 
diff --git a/libraries/shared/src/NodeList.cpp b/libraries/shared/src/NodeList.cpp
index aedfef9a3d..9a1317de88 100644
--- a/libraries/shared/src/NodeList.cpp
+++ b/libraries/shared/src/NodeList.cpp
@@ -263,7 +263,7 @@ void NodeList::addNodeTypeToInterestSet(NodeType_t nodeTypeToAdd) {
     _nodeTypesOfInterest << nodeTypeToAdd;
 }
 
-void NodeList::addSetOfNodeTypesToNodeInterestSet(const QSet& setOfNodeTypes) {
+void NodeList::addSetOfNodeTypesToNodeInterestSet(const NodeSet& setOfNodeTypes) {
     _nodeTypesOfInterest.unite(setOfNodeTypes);
 }
 
@@ -621,7 +621,7 @@ SharedNodePointer NodeList::addOrUpdateNode(const QUuid& uuid, char nodeType,
 }
 
 unsigned NodeList::broadcastToNodes(const QByteArray& packet,
-                                    const QSet& destinationNodeTypes) {
+                                    const NodeSet& destinationNodeTypes) {
     unsigned n = 0;
 
     foreach (const SharedNodePointer& node, getNodeHash()) {

From 4bb72b9f3f21d1cdcf4d03d66fe42b7966dc071d Mon Sep 17 00:00:00 2001
From: Stephen Birarda 
Date: Tue, 28 Jan 2014 13:44:47 -0800
Subject: [PATCH 14/16] remove MAX_HOSTNAME_BYTES

---
 libraries/shared/src/NodeList.h | 2 --
 1 file changed, 2 deletions(-)

diff --git a/libraries/shared/src/NodeList.h b/libraries/shared/src/NodeList.h
index b3ac019a42..6b8acd6e99 100644
--- a/libraries/shared/src/NodeList.h
+++ b/libraries/shared/src/NodeList.h
@@ -38,8 +38,6 @@ const quint64 PING_INACTIVE_NODE_INTERVAL_USECS = 1 * 1000 * 1000;
 
 extern const char SOLO_NODE_TYPES[2];
 
-const int MAX_HOSTNAME_BYTES = 256;
-
 extern const QString DEFAULT_DOMAIN_HOSTNAME;
 extern const unsigned short DEFAULT_DOMAIN_SERVER_PORT;
 

From 2dd71435eef709a10da279de9e9109755ae71c3a Mon Sep 17 00:00:00 2001
From: Stephen Birarda 
Date: Wed, 29 Jan 2014 12:25:05 -0800
Subject: [PATCH 15/16] fix build breakers for new packet type

---
 assignment-client/src/Agent.cpp | 9 +++++----
 1 file changed, 5 insertions(+), 4 deletions(-)

diff --git a/assignment-client/src/Agent.cpp b/assignment-client/src/Agent.cpp
index 7120f82bfc..84714259e5 100644
--- a/assignment-client/src/Agent.cpp
+++ b/assignment-client/src/Agent.cpp
@@ -28,7 +28,8 @@ Agent::Agent(const QByteArray& packet) :
 }
 
 void Agent::processDatagram(const QByteArray& dataByteArray, const HifiSockAddr& senderSockAddr) {
-    if (packetTypeForPacket(dataByteArray) == PacketTypeJurisdiction) {
+    PacketType datagramPacketType = packetTypeForPacket(dataByteArray);
+    if (datagramPacketType == PacketTypeJurisdiction) {
         int headerBytes = numBytesForPacketHeader(dataByteArray);
         // PacketType_JURISDICTION, first byte is the node type...
         switch (dataByteArray[headerBytes]) {
@@ -41,12 +42,12 @@ void Agent::processDatagram(const QByteArray& dataByteArray, const HifiSockAddr&
                                                                                                                dataByteArray);
                 break;
         }
-    } else if (dataByteArray[0] == PACKET_TYPE_PARTICLE_ADD_RESPONSE) {
+    } else if (datagramPacketType == PacketTypeParticleAddResponse) {
         // this will keep creatorTokenIDs to IDs mapped correctly
-        Particle::handleAddParticleResponse((unsigned char*) dataByteArray.data(), dataByteArray.size());
+        Particle::handleAddParticleResponse(dataByteArray);
         
         // also give our local particle tree a chance to remap any internal locally created particles
-        _particleTree.handleAddParticleResponse((unsigned char*) dataByteArray.data(), dataByteArray.size());
+        _particleTree.handleAddParticleResponse(dataByteArray);
     } else {
         NodeList::getInstance()->processNodeData(senderSockAddr, dataByteArray);
     }

From 7d8b7a79acccf9c5d76a33a10533f3f735b1ba1f Mon Sep 17 00:00:00 2001
From: Stephen Birarda 
Date: Wed, 29 Jan 2014 12:30:20 -0800
Subject: [PATCH 16/16] fix Particle update signature

---
 libraries/particles/src/Particle.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/libraries/particles/src/Particle.h b/libraries/particles/src/Particle.h
index 6cb26aba47..debb073ebd 100644
--- a/libraries/particles/src/Particle.h
+++ b/libraries/particles/src/Particle.h
@@ -290,7 +290,7 @@ public:
     
     void applyHardCollision(const CollisionInfo& collisionInfo);
 
-    void update(const uint64_t& now);
+    void update(const quint64& now);
     void collisionWithParticle(Particle* other);
     void collisionWithVoxel(VoxelDetail* voxel);