--- /dev/null
+#include "sockpool.h"
+
+sockPoolHashTable_t sockhash;
+
+inline int CompareAndSwap(int *a, int oldval, int newval) {
+ int temp = *a;
+ if (temp == oldval) {
+ *a = newval;
+ return 1;
+ } else
+ return 0;
+ return 1;
+}
+
+inline void InitLock(SpinLock *s) {
+ *s = 0;
+}
+
+inline void Lock(SpinLock *s) {
+ do {
+ } while(CompareAndSwap(s, 1, 1));
+}
+
+inline void UnLock(SpinLock *s) {
+ *s = 0;
+}
+
+int createSockPool(unsigned int size, float loadfactor) {
+ socknode_t **nodelist;
+ if ((nodelist = calloc(size, sizeof(socknode_t *))) < 0) {
+ printf("Calloc error at %s line %d\n", __FILE__, __LINE__);
+ return -1;
+ }
+ socknode_t **inuselist;
+ if ((inuselist = calloc(size, sizeof(socknode_t *))) < 0) {
+ printf("Calloc error at %s line %d\n", __FILE__, __LINE__);
+ free(nodelist);
+ return -1;
+ }
+ sockhash.table = nodelist;
+ sockhash.inuse = inuselist;
+ sockhash.size = size;
+ sockhash.numelements = 0;
+ sockhash.loadfactor = loadfactor;
+ InitLock(&sockhash.mylock);
+ return 0;
+}
+
+int createNewSocket(unsigned int mid) {
+ int sd;
+ if((sd = socket(AF_INET, SOCK_STREAM, 0)) < 0) {
+ printf("%s() Error: In creating socket at %s, %d\n", __func__, __FILE__, __LINE__);
+ return -1;
+ }
+ struct sockaddr_in remoteAddr;
+ bzero(&remoteAddr, sizeof(remoteAddr));
+ remoteAddr.sin_family = AF_INET;
+ remoteAddr.sin_port = htons(LISTEN_PORT);
+ remoteAddr.sin_addr.s_addr = htonl(mid);
+ if(connect(sd, (struct sockaddr *)&remoteAddr, sizeof(remoteAddr)) < 0) {
+ printf("%s(): Error %d connecting to %s:%d\n", __func__, errno, inet_ntoa(remoteAddr.sin_addr), LISTEN_PORT);
+ close(sd);
+ return -1;
+ }
+ return sd;
+}
+
+int getSock(unsigned int mid) {
+ int key = mid%(sockhash.size);
+
+ Lock(&sockhash.mylock);
+ if (sockhash.table[key] == NULL) {
+ UnLock(&sockhash.mylock);
+ int sd;
+ if((sd = createNewSocket(mid)) != -1) {
+ socknode_t *inusenode = calloc(1, sizeof(socknode_t));
+ inusenode->mid = mid;
+ inusenode->sd = sd;
+ insToList(inusenode);
+ return sd;
+ } else {
+ return -1;
+ }
+ }
+ UnLock(&sockhash.mylock);
+ int midFound = 0;
+ Lock(&sockhash.mylock);
+ socknode_t *ptr = sockhash.table[key];
+ while (ptr != NULL) {
+ if (mid == ptr->mid) {
+ midFound = 1;
+ int sd = ptr->sd;
+ UnLock(&sockhash.mylock);
+ insToList(ptr);
+ return sd;
+ }
+ ptr = ptr->next;
+ }
+ UnLock(&sockhash.mylock);
+ if(midFound == 0) {
+ int sd;
+ if((sd = createNewSocket(mid)) != -1) {
+ socknode_t *inusenode = calloc(1, sizeof(socknode_t));
+ inusenode->mid = mid;
+ inusenode->sd = sd;
+ insToList(inusenode);
+ return sd;
+ } else {
+ return -1;
+ }
+ }
+ return -1;
+}
+
+int insToList(socknode_t *inusenode) {
+ int key = (inusenode->mid)%(sockhash.size);
+ Lock(&sockhash.mylock);
+ inusenode->next = sockhash.inuse[key];
+ sockhash.inuse[key] = inusenode;
+ UnLock(&sockhash.mylock);
+ return 0;
+}
+
+int freeSock(unsigned int mid, int sd) {
+ int key = mid%(sockhash.size);
+
+ Lock(&sockhash.mylock);
+ socknode_t *ptr = sockhash.inuse[key];
+ ptr->mid = mid;
+ ptr->sd = sd;
+ sockhash.inuse[key] = ptr->next;
+ ptr->next = sockhash.table[key];
+ sockhash.table[key] = ptr;
+ UnLock(&sockhash.mylock);
+}
+
+int deleteSockpool(sockPoolHashTable_t *sockhash) {
+ free(sockhash->table);
+}
--- /dev/null
+#ifndef _SOCKPOOL_H_
+#define _SOCKPOOL_H_
+
+#include "dstm.h"
+
+#define LOADFACTOR 0.5
+
+typedef int SpinLock;
+
+typedef struct socknode {
+ int sd;
+ unsigned int mid;
+ struct socknode *next;
+} socknode_t;
+
+typedef struct sockPoolHashTable {
+ socknode_t **table;
+ socknode_t **inuse;
+ unsigned int size;
+ unsigned int numelements;
+ float loadfactor;
+ SpinLock mylock;
+} sockPoolHashTable_t;
+
+int createSockPool(unsigned int, float);
+int getSock(unsigned int);
+int freeSock(unsigned int, int);
+int deleteSockpool(sockPoolHashTable_t *);
+int insToList(socknode_t *);
+int createNewSocket(unsigned int);
+int CompareAndSwap(int *, int, int);
+void InitLock(SpinLock *);
+void Lock (SpinLock *);
+void UnLock (SpinLock *);
+
+#endif