X-Git-Url: http://git.liburcu.org/?a=blobdiff_plain;f=lttv%2Flttv%2Fsync%2Fdata_structures.c;h=79b8963d61427d83b48a2feebb2051c471a2322b;hb=b2da0724a95cdb911c07640268b65bd9c5b92010;hp=70eb22c74a84f6d56f957f2d81da5f4d4422072e;hpb=f6691532b67cb6911749118e3da8d74de876380c;p=lttv.git diff --git a/lttv/lttv/sync/data_structures.c b/lttv/lttv/sync/data_structures.c index 70eb22c7..79b8963d 100644 --- a/lttv/lttv/sync/data_structures.c +++ b/lttv/lttv/sync/data_structures.c @@ -1,19 +1,18 @@ /* This file is part of the Linux Trace Toolkit viewer - * Copyright (C) 2009 Benjamin Poirier + * Copyright (C) 2009, 2010 Benjamin Poirier * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License Version 2 as - * published by the Free Software Foundation; + * This program is free software: you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation, either version 2.1 of the License, or (at + * your option) any later version. * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + * License for more details. * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place - Suite 330, Boston, - * MA 02111-1307, USA. + * You should have received a copy of the GNU Lesser General Public License + * along with this program. If not, see . */ #ifdef HAVE_CONFIG_H @@ -34,10 +33,6 @@ #include "data_structures.h" -#ifndef g_info -#define g_info(format...) g_log (G_LOG_DOMAIN, G_LOG_LEVEL_INFO, format) -#endif - // TCP sequence numbers use clock arithmetic, these comparison functions take // that into account #define SEQ_LT(a,b) ((int32_t)((a)-(b)) < 0) @@ -45,6 +40,15 @@ #define SEQ_GT(a,b) ((int32_t)((a)-(b)) > 0) #define SEQ_GEQ(a,b) ((int32_t)((a)-(b)) >= 0) +const char* const approxNames[]= { + [EXACT]= "Exact", + [ACCURATE]= "Accurate", + [APPROXIMATE]= "Approximate", + [INCOMPLETE]= "Incomplete", + [ABSENT]= "Absent", + [SCREWED]= "Screwed", +}; + /* * Compare two ConnectionKey structures @@ -99,15 +103,12 @@ bool isAcking(const Message* const ackSegment, const Message* const * Convert an IP address from 32 bit form to dotted quad * * Args: - * str: A preallocated string of length >= 17 + * str: A preallocated string of length >= 16 * addr: Address */ void convertIP(char* const str, const uint32_t addr) { - struct in_addr iaddr; - - iaddr.s_addr= htonl(addr); - strcpy(str, inet_ntoa(iaddr)); + strcpy(str, inet_ntoa((struct in_addr) {.s_addr= addr})); } @@ -116,7 +117,7 @@ void convertIP(char* const str, const uint32_t addr) */ void printTCPSegment(const Message* const segment) { - char saddr[17], daddr[17]; + char saddr[16], daddr[16]; SegmentKey* segmentKey; g_assert(segment->inE->type == TCP); @@ -241,8 +242,6 @@ void gdnTCPSegmentListDestroy(gpointer data) list= (GQueue*) data; - g_debug("XXXX gdnTCPSegmentListDestroy\n"); - g_queue_foreach(list, &gfTCPSegmentDestroy, NULL); g_queue_free(list); } @@ -257,7 +256,6 @@ void gdnTCPSegmentListDestroy(gpointer data) */ void gfTCPSegmentDestroy(gpointer data, gpointer user_data) { - g_debug("XXXX gfTCPSegmentDestroy\n"); destroyTCPSegment((Message*) data); } @@ -273,7 +271,6 @@ void destroyTCPSegment(Message* const segment) { TCPEvent* inE, *outE; - g_debug("XXXX destroyTCPSegment"); segment->print(segment); g_assert(segment->inE != NULL && segment->outE != NULL); @@ -329,6 +326,7 @@ void destroyTCPEvent(Event* const event) destroyEvent(event); } + /* * Free the memory used by a base Event */ @@ -464,9 +462,14 @@ void gdnConnectionKeyDestroy(gpointer data) guint ghfDatagramKeyHash(gconstpointer key) { DatagramKey* datagramKey; + union { + uint8_t byteKey[8]; + uint32_t hashableKey[2]; + } dataKey; uint32_t a, b, c; datagramKey= (DatagramKey*) key; + memcpy(dataKey.byteKey, datagramKey->dataKey, sizeof(dataKey.byteKey)); a= datagramKey->saddr; b= datagramKey->daddr; @@ -474,8 +477,8 @@ guint ghfDatagramKeyHash(gconstpointer key) mix(a, b, c); a+= datagramKey->ulen; // 16 bits left here - b+= *((uint32_t*) datagramKey->dataKey); - c+= *((uint32_t*) ((void*) datagramKey->dataKey + 4)); + b+= dataKey.hashableKey[0]; + c+= dataKey.hashableKey[1]; final(a, b, c); return c; @@ -545,7 +548,7 @@ void gdnDestroyBroadcast(gpointer data) void destroyBroadcast(Broadcast* const broadcast) { g_queue_foreach(broadcast->events, &gfDestroyEvent, NULL); - g_queue_clear(broadcast->events); + g_queue_free(broadcast->events); free(broadcast); } @@ -563,3 +566,190 @@ void gfDestroyEvent(gpointer data, gpointer user_data) event->destroy(event); } + + +/* Subtract two WallTime structs + * + * Args: + * tA, tB: WallTime + * + * Returns: + * The result of tA - tB, as a double. This may incur a loss of + * precision. + */ +double wallTimeSub(const WallTime const* tA, const WallTime const* tB) +{ + return (double) tA->seconds - tB->seconds + ((double) tA->nanosec - tB->nanosec) / 1e9; +} + + +/* + * Allocate and copy a base event + * + * Args: + * newEvent: new event, pointer will be updated + * event: event to copy + */ +void copyEvent(const Event* const event, Event** const newEvent) +{ + g_assert(event->event.tcpEvent == NULL); + + *newEvent= malloc(sizeof(Event)); + memcpy(*newEvent, event, sizeof(Event)); +} + + +/* + * Allocate and copy a TCP event + * + * Args: + * newEvent: new event, pointer will be updated + * event: event to copy + */ +void copyTCPEvent(const Event* const event, Event** const newEvent) +{ + g_assert(event->type == TCP); + + *newEvent= malloc(sizeof(Event)); + memcpy(*newEvent, event, sizeof(Event)); + + (*newEvent)->event.tcpEvent= malloc(sizeof(TCPEvent)); + memcpy((*newEvent)->event.tcpEvent, event->event.tcpEvent, + sizeof(TCPEvent)); + + (*newEvent)->event.tcpEvent->segmentKey= malloc(sizeof(SegmentKey)); + memcpy((*newEvent)->event.tcpEvent->segmentKey, + event->event.tcpEvent->segmentKey, sizeof(SegmentKey)); +} + + +/* + * Allocate and copy a UDP event + * + * Args: + * newEvent: new event, pointer will be updated + * event: event to copy + */ +void copyUDPEvent(const Event* const event, Event** const newEvent) +{ + g_assert(event->type == UDP); + + *newEvent= malloc(sizeof(Event)); + memcpy(*newEvent, event, sizeof(Event)); + + (*newEvent)->event.udpEvent= malloc(sizeof(UDPEvent)); + memcpy((*newEvent)->event.udpEvent, event->event.udpEvent, + sizeof(UDPEvent)); + + (*newEvent)->event.udpEvent->datagramKey= malloc(sizeof(DatagramKey)); + memcpy((*newEvent)->event.udpEvent->datagramKey, + event->event.udpEvent->datagramKey, sizeof(DatagramKey)); +} + + +/* + * A GFunc for g_queue_foreach() + * + * Args: + * data Event*, event to add + * user_data GArray*, array to add to + */ +void gfAddEventToArray(gpointer data, gpointer user_data) +{ + g_array_append_val((GArray*) user_data, data); +} + + +/* + * Free a PairFactors + * + * Args: + * factorsCHull: container of Factors + */ +void destroyPairFactors(PairFactors* pairFactors) +{ + if (pairFactors->min != NULL) + { + free(pairFactors->min); + } + if (pairFactors->max != NULL) + { + free(pairFactors->max); + } + if (pairFactors->approx != NULL) + { + free(pairFactors->approx); + } +} + + +/* + * Create and initialize a container of PairFactors + * + * Args: + * traceNb: number of traces + * + * Returns: + * A new array, which can be freed with freeAllFactors() + */ +AllFactors* createAllFactors(const unsigned int traceNb) +{ + AllFactors* allFactors; + PairFactors** factorsArray; + unsigned int i, j; + + allFactors= malloc(sizeof(AllFactors)); + allFactors->refCount= 1; + allFactors->pairFactors= malloc(traceNb * sizeof(PairFactors*)); + factorsArray=allFactors->pairFactors; + for (i= 0; i < traceNb; i++) + { + factorsArray[i]= calloc(traceNb, sizeof(PairFactors)); + + for (j= 0; j < traceNb; j++) + { + if (i == j) + { + factorsArray[i][i].type= EXACT; + factorsArray[i][i].approx= malloc(sizeof(Factors)); + factorsArray[i][i].approx->drift= 1.; + factorsArray[i][i].approx->offset= 0.; + } + else + { + factorsArray[i][j].type= ABSENT; + } + } + } + + return allFactors; +} + + +/* + * Free a container of PairFactors + * + * Args: + * allFactors: container of PairFactors + * traceNb: number of traces + */ +void freeAllFactors(AllFactors* const allFactors, const unsigned int traceNb) +{ + unsigned int i, j; + + allFactors->refCount--; + + if (allFactors->refCount == 0) + { + for (i= 0; i < traceNb; i++) + { + for (j= 0; j < traceNb; j++) + { + destroyPairFactors(&allFactors->pairFactors[i][j]); + } + free(allFactors->pairFactors[i]); + } + free(allFactors->pairFactors); + free(allFactors); + } +}