int rtaComponent_PutMessage(PARCEventQueue *queue, TransportMessage *tm) { RtaConnection *conn = rtaConnection_GetFromTransport(tm); assertNotNull(conn, "Got null connection from transport message\n"); if (rtaConnection_GetState(conn) != CONN_CLOSED) { PARCEventBuffer *out = parcEventBuffer_GetQueueBufferOutput(queue); int res; rtaConnection_IncrementMessagesInQueue(conn); if (DEBUG_OUTPUT) { printf("%s queue %-12s tm %p\n", __func__, rtaProtocolStack_GetQueueName(rtaConnection_GetStack(conn), queue), (void *) tm); } res = parcEventBuffer_Append(out, (void *)&tm, sizeof(&tm)); assertTrue(res == 0, "%s parcEventBuffer_Append returned error\n", __func__); parcEventBuffer_Destroy(&out); return 1; } else { // should increment a drop counter (case 908) transportMessage_Destroy(&tm); return 0; } }
LONGBOW_TEST_CASE(Global, metisMessage_Copy) { char message_str[] = "\x00Once upon a time, in a stack far away, a dangling pointer found its way to the top of the heap."; PARCEventBuffer *buff = parcEventBuffer_Create(); parcEventBuffer_Append(buff, message_str, sizeof(message_str)); PARCLogReporter *reporter = parcLogReporterTextStdout_Create(); MetisLogger *logger = metisLogger_Create(reporter, parcClock_Wallclock()); parcLogReporter_Release(&reporter); MetisMessage *message = metisMessage_CreateFromBuffer(1, 2, buff, logger); metisLogger_Release(&logger); assertNotNull(message, "Got null from metisMessage_CreateFromBuffer"); assertTrue(message->refcount == 1, "Incorrect refcount, expected %u got %u", 1, message->refcount); MetisMessage *copy = metisMessage_Acquire(message); assertTrue(message->refcount == 2, "Incorrect refcount, expected %u got %u", 2, message->refcount); metisMessage_Release(&message); assertTrue(copy->refcount == 1, "Incorrect refcount, expected %u got %u", 1, message->refcount); metisMessage_Release(©); assertTrue(parcMemory_Outstanding() == 0, "Memory balance should be zero after destroying last copy, got %u", parcMemory_Outstanding()); }
/** * Reads from the socket to fill in the work buffer * * Reads one or more packets from the socket to the work buffer It will append to the work buffer. * The BFP socket is non-blocking. The BPF interface may return multiple packets in one read * that need to be parsed as in _darwinEthernet_ReadWorkBuffer(). * * @param [in] ether The Darwin ethernet interface * * @retval true We added something to the work buffer * @retval false Nothing was read * * Example: * @code * <#example#> * @endcode */ static bool _darwinEthernet_ReadSocket(MetisGenericEther *ether) { bool success = false; if (metisLogger_IsLoggable(ether->logger, MetisLoggerFacility_IO, PARCLogLevel_Debug)) { metisLogger_Log(ether->logger, MetisLoggerFacility_IO, PARCLogLevel_Debug, __func__, "%s reading fd %d bufferLength %u", __func__, ether->etherSocket, ether->etherBufferLength); } // The buffer we're reading must be exactly ether->etherBufferLength // TODO: Fix the parcEventBuffer_ReadFromFileDescriptor call to reserve that space so it's all there. uint8_t tempBuffer[ether->etherBufferLength]; ssize_t read_length = read(ether->etherSocket, tempBuffer, ether->etherBufferLength); if (read_length > 0) { parcEventBuffer_Append(ether->workBuffer, tempBuffer, read_length); if (read_length > 0) { if (metisLogger_IsLoggable(ether->logger, MetisLoggerFacility_IO, PARCLogLevel_Debug)) { metisLogger_Log(ether->logger, MetisLoggerFacility_IO, PARCLogLevel_Debug, __func__, "%s read %zd bytes from fd %d", __func__, read_length, ether->etherSocket); } success = true; } } return success; }
LONGBOW_TEST_CASE(Global, metisMessage_ReadFromBuffer) { char message_str[] = "\x00Once upon a time, in a stack far away, a dangling pointer found its way to the top of the heap."; PARCEventBuffer *buff = parcEventBuffer_Create(); parcEventBuffer_Append(buff, message_str, sizeof(message_str)); PARCLogReporter *reporter = parcLogReporterTextStdout_Create(); MetisLogger *logger = metisLogger_Create(reporter, parcClock_Wallclock()); parcLogReporter_Release(&reporter); MetisMessage *message = metisMessage_ReadFromBuffer(1, 2, buff, sizeof(message_str), logger); metisLogger_Release(&logger); assertNotNull(message, "Got null from metisMessage_CreateFromBuffer"); assertTrue(parcEventBuffer_GetLength(message->messageBytes) == sizeof(message_str), "Length of internal buffer wrong, expected %zu got %zu", sizeof(message_str), parcEventBuffer_GetLength(message->messageBytes)); uint8_t *p = parcEventBuffer_Pullup(message->messageBytes, sizeof(message_str)); assertTrue(memcmp(p, message_str, sizeof(message_str)) == 0, "Internal buffer contents does not match test"); assertTrue(message->ingressConnectionId == 1, "IngressConnectionId wrong, expected %d got %u", 1, message->ingressConnectionId); assertTrue(message->receiveTime == 2, "receiveTime wrong, expected %u got %" PRIu64, 2, message->receiveTime); assertTrue(parcEventBuffer_GetLength(buff) == 0, "Origin buffer not drained, expected 0, got %zu", parcEventBuffer_GetLength(buff)); metisMessage_Release(&message); parcEventBuffer_Destroy(&buff); }
LONGBOW_TEST_CASE(Global, metisMessage_HasInterestLifetime) { PARCEventBuffer *buff = parcEventBuffer_Create(); parcEventBuffer_Append(buff, metisTestDataV1_Interest_AllFields, sizeof(metisTestDataV1_Interest_AllFields)); PARCLogReporter *reporter = parcLogReporterTextStdout_Create(); MetisLogger *logger = metisLogger_Create(reporter, parcClock_Wallclock()); parcLogReporter_Release(&reporter); MetisMessage *message = metisMessage_CreateFromBuffer(1, 2, buff, logger); metisLogger_Release(&logger); assertTrue(metisMessage_HasInterestLifetime(message), "Should have returned true for interest lifetime"); metisMessage_Release(&message); }
LONGBOW_TEST_CASE(Global, metisMessage_GetInterestLifetimeTicks) { PARCEventBuffer *buff = parcEventBuffer_Create(); parcEventBuffer_Append(buff, metisTestDataV1_Interest_AllFields, sizeof(metisTestDataV1_Interest_AllFields)); PARCLogReporter *reporter = parcLogReporterTextStdout_Create(); MetisLogger *logger = metisLogger_Create(reporter, parcClock_Wallclock()); parcLogReporter_Release(&reporter); MetisMessage *message = metisMessage_CreateFromBuffer(1, 2, buff, logger); metisLogger_Release(&logger); // don't check actual value. It will vary based on METISHZ and rouding errors due to integer math MetisTicks ticks = metisMessage_GetInterestLifetimeTicks(message); assertTrue(ticks > 0, "Should have gotten positive value for interest lifetime ticks"); metisMessage_Release(&message); }
LONGBOW_TEST_CASE(Global, metisMessage_Create_InterestV1) { PARCEventBuffer *buff = parcEventBuffer_Create(); parcEventBuffer_Append(buff, metisTestDataV1_Interest_AllFields, sizeof(metisTestDataV1_Interest_AllFields)); PARCLogReporter *reporter = parcLogReporterTextStdout_Create(); MetisLogger *logger = metisLogger_Create(reporter, parcClock_Wallclock()); parcLogReporter_Release(&reporter); MetisMessage *message = metisMessage_CreateFromBuffer(1, 2, buff, logger); metisLogger_Release(&logger); assertNotNull(message, "Got null from metisMessage_CreateFromBuffer"); assertTrue(message->ingressConnectionId == 1, "IngressConnectionId wrong, expected %d got %u", 1, message->ingressConnectionId); assertTrue(message->receiveTime == 2, "receiveTime wrong, expected %u got %" PRIu64, 2, message->receiveTime); metisMessage_Release(&message); }
LONGBOW_TEST_CASE(Global, metisMessage_CreateFromBuffer_BadMessage) { // Bad version char message_str[] = "\xFFOnce upon a time, in a stack far away, a dangling pointer found its way to the top of the heap."; printf("metisMessage_CreateFromBuffer_BadMessage attempting to process a bad message which should report an error:\n"); PARCEventBuffer *buff = parcEventBuffer_Create(); parcEventBuffer_Append(buff, message_str, sizeof(message_str)); PARCLogReporter *reporter = parcLogReporterTextStdout_Create(); MetisLogger *logger = metisLogger_Create(reporter, parcClock_Wallclock()); parcLogReporter_Release(&reporter); MetisMessage *message = metisMessage_CreateFromBuffer(1, 2, buff, logger); metisLogger_Release(&logger); assertNull(message, "Got null from metisMessage_CreateFromBuffer"); }
LONGBOW_TEST_CASE(Global, metisMessage_Length) { char message_str[] = "\x00Once upon a time, in a stack far away, a dangling pointer found its way to the top of the heap."; PARCEventBuffer *buff = parcEventBuffer_Create(); parcEventBuffer_Append(buff, message_str, sizeof(message_str)); PARCLogReporter *reporter = parcLogReporterTextStdout_Create(); MetisLogger *logger = metisLogger_Create(reporter, parcClock_Wallclock()); parcLogReporter_Release(&reporter); MetisMessage *message = metisMessage_CreateFromBuffer(1, 2, buff, logger); metisLogger_Release(&logger); assertNotNull(message, "Got null from metisMessage_CreateFromBuffer"); size_t length = metisMessage_Length(message); assertTrue(length == sizeof(message_str), "Wrong length, expected %zu got %zu", sizeof(message_str), length); metisMessage_Release(&message); }
LONGBOW_TEST_CASE(Global, metisMessage_GetReceiveTime) { char message_str[] = "\x00Once upon a time, in a stack far away, a dangling pointer found its way to the top of the heap."; PARCEventBuffer *buff = parcEventBuffer_Create(); parcEventBuffer_Append(buff, message_str, sizeof(message_str)); PARCLogReporter *reporter = parcLogReporterTextStdout_Create(); MetisLogger *logger = metisLogger_Create(reporter, parcClock_Wallclock()); parcLogReporter_Release(&reporter); MetisMessage *message = metisMessage_CreateFromBuffer(1, 2, buff, logger); metisLogger_Release(&logger); assertNotNull(message, "Got null from metisMessage_CreateFromBuffer"); MetisTicks time = metisMessage_GetReceiveTime(message); assertTrue(time == 2, "Wrong receive time, expected %u got %" PRIu64, 2, time); metisMessage_Release(&message); }
LONGBOW_TEST_CASE(Global, metisMessage_Append) { char message_str[] = "\x00Once upon a time ..."; PARCEventBuffer *buffer = parcEventBuffer_Create(); PARCEventBuffer *buff = parcEventBuffer_Create(); parcEventBuffer_Append(buff, message_str, sizeof(message_str)); PARCLogReporter *reporter = parcLogReporterTextStdout_Create(); MetisLogger *logger = metisLogger_Create(reporter, parcClock_Wallclock()); parcLogReporter_Release(&reporter); MetisMessage *message = metisMessage_CreateFromBuffer(1, 2, buff, logger); int result = metisMessage_Append(buffer, message); assertTrue(result == 0, "Got error from metisMessage_Append"); metisLogger_Release(&logger); metisMessage_Release(&message); parcEventBuffer_Destroy(&buffer); }
LONGBOW_TEST_CASE(Global, metisMessage_Write) { char message_str[] = "\x00Once upon a time ..."; PARCEventScheduler *scheduler = parcEventScheduler_Create(); PARCEventQueue *queue = parcEventQueue_Create(scheduler, -1, PARCEventQueueOption_CloseOnFree); PARCEventBuffer *buff = parcEventBuffer_Create(); parcEventBuffer_Append(buff, message_str, sizeof(message_str)); PARCLogReporter *reporter = parcLogReporterTextStdout_Create(); MetisLogger *logger = metisLogger_Create(reporter, parcClock_Wallclock()); parcLogReporter_Release(&reporter); MetisMessage *message = metisMessage_CreateFromBuffer(1, 2, buff, logger); int result = metisMessage_Write(queue, message); assertTrue(result == 0, "Got error from metisMessage_Write"); // buff is deallocated by metisMessage_Release metisLogger_Release(&logger); metisMessage_Release(&message); parcEventQueue_Destroy(&queue); parcEventScheduler_Destroy(&scheduler); }