#include "URL.h"
#include "Mac.h"
#include "Table.h"
+#include "Slot.h"
#include "Crypto.h"
#include "ByteBuffer.h"
+#include <sys/socket.h>
+#include <unistd.h>
/**
* Empty Constructor needed for child class.
listeningPort(-1),
localServerThread(NULL),
doEnd(false),
- timer(TimingSingleton_getInstance())
+ timer(TimingSingleton_getInstance()),
+ getslot(new Array<char>("getslot", 7)),
+ putslot(new Array<char>("putslot", 7))
{
}
return 0;
}
+int createSocket(IoTString *host, int port) {
+ return 0;
+}
+
+int createSocket(int port) {
+ return 0;
+}
+
+int acceptSocket(int socket) {
+ return 0;
+}
+
+void writeSocketData(int fd, Array<char> *data) {}
+
+void writeSocketInt(int fd, int value) {}
+
+int readSocketInt(int fd) {return 0;}
+
+void readSocketData(int fd, Array<char> *data) {}
+
void writeURLData(int fd, Array<char> *data) {
}
if (responsecode != HttpURLConnection_HTTP_OK) {
throw new Error("Invalid response");
}
- if (is->available() > 0) {
- int salt_length = readURLInt(fd);
- Array<char> *tmp = new Array<char>(salt_length);
- readURLData(fd, tmp);
- salt = tmp;
- timer->endTime();
- return true;
- } else {
- timer->endTime();
- return false;
- }
+ int salt_length = readURLInt(fd);
+ Array<char> *tmp = new Array<char>(salt_length);
+ readURLData(fd, tmp);
+ salt = tmp;
+ timer->endTime();
+ return true;
} catch (SocketTimeoutException *e) {
timer->endTime();
throw new ServerException("getSalt failed", ServerException_TypeInputTimeout);
return buffer->array();
}
+Array<char> *AESEncrypt(Array<char> * ivBytes, AESKey * key, Array<char> * data) {
+ return NULL;
+}
+
+Array<char> *AESDecrypt(Array<char> * ivBytes, AESKey * key, Array<char> * data) {
+ return NULL;
+}
+
Array<char> *CloudComm::encryptSlotAndPrependIV(Array<char> *rawData, Array<char> *ivBytes) {
try {
- IvParameterSpec *ivSpec = new IvParameterSpec(ivBytes);
- Cipher *cipher = Cipher_getInstance("AES/CTR/NoPadding");
- cipher->init(Cipher_ENCRYPT_MODE, key, ivSpec);
- Array<char> *encryptedBytes = cipher->doFinal(rawData);
+ Array<char> *encryptedBytes = AESEncrypt(ivBytes, key, rawData);
Array<char> *chars = new Array<char>(encryptedBytes->length() + CloudComm_IV_SIZE);
System_arraycopy(ivBytes, 0, chars, 0, ivBytes->length());
System_arraycopy(encryptedBytes, 0, chars, CloudComm_IV_SIZE, encryptedBytes->length());
Array<char> *encryptedBytes = new Array<char>(rawData->length() - CloudComm_IV_SIZE);
System_arraycopy(rawData, 0, ivBytes, 0, CloudComm_IV_SIZE);
System_arraycopy(rawData, CloudComm_IV_SIZE, encryptedBytes, 0, encryptedBytes->length());
- IvParameterSpec *ivSpec = new IvParameterSpec(ivBytes);
- Cipher *cipher = Cipher_getInstance("AES/CTR/NoPadding");
- cipher->init(Cipher_DECRYPT_MODE, key, ivSpec);
- return cipher->doFinal(encryptedBytes);
+ return AESDecrypt(ivBytes, key, encryptedBytes);
} catch (Exception *e) {
throw new Error("Failed To Decrypt");
}
readURLData(fd, resptype);
timer->endTime();
- if (resptype->equals("getslot"->getBytes())) {
+ if (resptype->equals(getslot)) {
return processSlots(fd);
- } else if (resptype->equals("putslot"->getBytes())) {
+ } else if (resptype->equals(putslot)) {
return NULL;
} else
throw new Error("Bad response to putslot");
} catch (SocketTimeoutException *e) {
timer->endTime();
- throw new ServerException("putSlot failed", ServerException->TypeInputTimeout);
+ throw new ServerException("putSlot failed", ServerException_TypeInputTimeout);
} catch (Exception *e) {
throw new Error("putSlot failed");
}
* sequencenumber or newer->
*/
Array<Slot *> *CloudComm::getSlots(int64_t sequencenumber) {
+ int fd = -1;
try {
if (salt == NULL) {
if (!getSalt()) {
IoTString *url = buildRequest(false, sequencenumber, 0);
timer->startTime();
- URLConnection *con = url->openConnection();
- HttpURLConnection *http = (HttpURLConnection *) con;
- http->setRequestMethod("POST");
- http->setConnectTimeout(CloudComm_TIMEOUT_MILLIS);
- http->setReadTimeout(CloudComm_TIMEOUT_MILLIS);
- http->connect();
+ fd = openURL(url, true);
timer->endTime();
} catch (SocketTimeoutException *e) {
timer->endTime();
Array<char> *resptype = new Array<char>(7);
readURLData(fd, resptype);
timer->endTime();
- if (!resptype->equals("getslot"->getBytes()))
- throw new Error("Bad Response: " + new String(resptype));
+ if (!resptype->equals(getslot))
+ throw new Error("Bad Response: ");
- return processSlots(dis);
+ return processSlots(fd);
} catch (SocketTimeoutException *e) {
timer->endTime();
throw new ServerException("getSlots failed", ServerException_TypeInputTimeout);
sizesofslots->set(i, readURLInt(fd));
for (int i = 0; i < numberofslots; i++) {
Array<char> *rawData = new Array<char>(sizesofslots->get(i));
- readURLData(rawData);
+ readURLData(fd, rawData);
Array<char> *data = stripIVAndDecryptSlot(rawData);
slots->set(i, Slot_decode(table, data, mac));
}
return slots;
}
-Array<char> *CloudComm::sendLocalData(Array<char> *sendData, int64_t localSequenceNumber, String host, int port) {
+Array<char> *CloudComm::sendLocalData(Array<char> *sendData, int64_t localSequenceNumber, IoTString * host, int port) {
if (salt == NULL)
return NULL;
try {
Array<char> *encryptedData = encryptSlotAndPrependIV(totalData, iv);
// Open a TCP socket connection to a local device
- Socket *socket = new Socket(host, port);
- socket->setReuseAddress(true);
- DataOutputStream *output = new DataOutputStream(socket->getOutputStream());
- DataInputStream *input = new DataInputStream(socket->getInputStream());
+ int socket = createSocket(host, port);
timer->startTime();
// Send data to output (length of data, the data)
- output->writeInt(encryptedData->length());
- output->write(encryptedData, 0, encryptedData->length());
- output->flush();
+ writeSocketInt(socket, encryptedData->length());
+ writeSocketData(socket, encryptedData);
- int lengthOfReturnData = input->readInt();
+ int lengthOfReturnData = readSocketInt(socket);
Array<char> *returnData = new Array<char>(lengthOfReturnData);
- input->readFully(returnData);
+ readSocketData(socket, returnData);
timer->endTime();
returnData = stripIVAndDecryptSlot(returnData);
// We are done with this socket
- socket->close();
+ close(socket);
mac->update(returnData, 0, returnData->length() - CloudComm_HMAC_SIZE);
Array<char> *realmac = mac->doFinal();
Array<char> *recmac = new Array<char>(CloudComm_HMAC_SIZE);
}
void CloudComm::localServerWorkerFunction() {
- ServerSocket *inputSocket = NULL;
+ int inputSocket = -1;
try {
// Local server socket
- inputSocket = new ServerSocket(listeningPort);
- inputSocket->setReuseAddress(true);
- inputSocket->setSoTimeout(CloudComm_TIMEOUT_MILLIS);
+ inputSocket = createSocket(listeningPort);
} catch (Exception *e) {
throw new Error("Local server setup failure...");
}
while (!doEnd) {
try {
// Accept incoming socket
- Socket *socket = inputSocket->accept();
- DataInputStream *input = new DataInputStream(socket->getInputStream());
- DataOutputStream *output = new DataOutputStream(socket->getOutputStream());
+ int socket = acceptSocket(inputSocket);
// Get the encrypted data from the server
- int dataSize = input->readInt();
+ int dataSize = readSocketInt(socket);
Array<char> *readData = new Array<char>(dataSize);
- input->readFully(readData);
+ readSocketData(socket, readData);
timer->endTime();
// Decrypt the data
timer->startTime();
// Send data to output (length of data, the data)
- output->writeInt(encryptedData->length());
- output->write(encryptedData, 0, encryptedData->length());
- output->flush();
-
- // close the socket
- socket->close();
+ writeSocketInt(socket, encryptedData->length());
+ writeSocketData(socket, encryptedData);
+ close(socket);
} catch (Exception *e) {
}
}
- if (inputSocket != NULL) {
+ if (inputSocket != -1) {
try {
- inputSocket->close();
+ close(inputSocket);
} catch (Exception *e) {
throw new Error("Local server close failure...");
}
}
}
-void CloudComm::close() {
+void CloudComm::closeCloud() {
doEnd = true;
if (localServerThread != NULL) {