Commit fbfd14b0 authored by Andreas Schmidt's avatar Andreas Schmidt

Refactor. Proper creation of feedback packets.

parent cd011141
......@@ -7,10 +7,14 @@ set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/bin)
add_subdirectory(prrt)
add_library(PRRT prrt/socket.c prrt/block.c prrt/block.h prrt/packet.c prrt/packet.h)
add_library(UTIL util/common.c util/common.h)
add_executable(sender sender.c)
add_executable(receiver receiver.c)
add_executable(tester tester.c)
target_link_libraries(sender LINK_PUBLIC PRRT)
target_link_libraries(receiver LINK_PUBLIC PRRT)
target_link_libraries(tester LINK_PUBLIC PRRT)
\ No newline at end of file
target_link_libraries(tester LINK_PUBLIC PRRT)
target_link_libraries(sender LINK_PUBLIC UTIL)
target_link_libraries(receiver LINK_PUBLIC UTIL)
target_link_libraries(tester LINK_PUBLIC UTIL)
\ No newline at end of file
//
// Created by andreas on 06.11.15.
//
#include <stdlib.h>
#include <stdio.h>
#include <sys/time.h>
......@@ -20,27 +16,92 @@ uint16_t packet_size(prrt_packet *packet_ptr) {
return (uint16_t) (packet_ptr->payload_len + PRRT_PACKET_GENERAL_HEADER_SIZE); // 4 = 4bit type + 4bit priority + 8 bit index + 16bit seqno
}
int print_packet(prrt_packet *packet_ptr) {
printf("+------+------+----------+------------------+\n");
printf("| %4u | %4u | %8u | %16u |\n", packet_type(packet_ptr), packet_priority(packet_ptr), packet_ptr->index, packet_ptr->seqno);
uint8_t type = packet_type(packet_ptr);
printf("| %4u | %4u | %8u | %16u |\n", type, packet_priority(packet_ptr), packet_ptr->index, packet_ptr->seqno);
printf("+------------------------+------------------+\n");
if(packet_type(packet_ptr) == PACKET_TYPE_SOURCE) {
if(type == PACKET_TYPE_SOURCE) {
prrt_packet_source_payload * payload = packet_ptr->payload;
printf("| %32u |\n", payload->timestamp);
printf("+---------------------+---------------------+\n");
printf("| %16u | %16u |\n", payload->rtt, payload->packet_timeout);
printf("| %16u | %16u |\n", payload->round_trip_time, payload->packet_timeout);
printf("+---------------------+---------------------+\n");
}
else if(type == PACKET_TYPE_FEEDBACK) {
prrt_packet_feedback_payload * payload = packet_ptr->payload;
printf("| %32u |\n", payload->round_trip_time);
printf("| %32u |\n", payload->packet_loss_rate);
printf("| %32u |\n", payload->burstiness_coefficient);
printf("| %32u |\n", payload->bandwidth);
printf("| %32u |\n", payload->feedback_block);
printf("+-------------------------------------------+\n");
} else {
printf("| Unhandeled Type |\n");
printf("+-------------------------------------------+\n");
}
return 0;
}
int encode_packet(void *buf_ptr, uint16_t buf_size, prrt_packet *packet) {
void * payload = packet->payload;
if(buf_size < packet->payload_len + PRRT_PACKET_GENERAL_HEADER_SIZE) {
perror("BUFER TO SMALL");
return -1;
}
memcpy(buf_ptr, packet, PRRT_PACKET_GENERAL_HEADER_SIZE);
buf_ptr += PRRT_PACKET_GENERAL_HEADER_SIZE;
uint8_t type = packet_type(packet);
if(type == PACKET_TYPE_SOURCE) {
memcpy(buf_ptr, payload, PRRT_PACKET_SOURCE_HEADER_SIZE);
buf_ptr += PRRT_PACKET_SOURCE_HEADER_SIZE;
memcpy(buf_ptr, payload + PRRT_PACKET_SOURCE_HEADER_SIZE, packet->payload_len - PRRT_PACKET_SOURCE_HEADER_SIZE);
} else if (type == PACKET_TYPE_FEEDBACK) {
memcpy(buf_ptr, payload, PRRT_PACKET_FEEDBACK_SIZE);
} else {
perror("NOT IMPLEMENTED");
return -1;
}
return 0;
}
int decode_packet(void *buf_ptr, uint16_t buf_size, prrt_packet *packet_ptr) {
uint32_t payload_len = (uint32_t) (buf_size - PRRT_PACKET_GENERAL_HEADER_SIZE);
packet_ptr->type_priority = *(uint8_t*) buf_ptr;
uint8_t* index_ptr = (uint8_t*) (buf_ptr+1);
packet_ptr->index = *index_ptr;
uint16_t* seqno_prt = (uint16_t*) (buf_ptr+2);
packet_ptr->seqno = *seqno_prt;
unsigned char* payload_buffer = malloc(payload_len);
memcpy(payload_buffer, buf_ptr + PRRT_PACKET_GENERAL_HEADER_SIZE, payload_len);
packet_ptr->payload = payload_buffer;
packet_ptr->payload_len = payload_len;
return 0;
}
int delete_packet(prrt_packet *packet_ptr) {
if(packet_ptr->payload != NULL) {
free(packet_ptr->payload);
}
free(packet_ptr);
return 0;
}
// PACKET SPECIFIC CODE
int create_packet_source(prrt_packet *packet_ptr, uint8_t priority, const void * data_ptr, unsigned long data_len) {
packet_ptr->type_priority = PACKET_TYPE_SOURCE << 4;
packet_ptr->type_priority |= priority & 0x0F;
packet_ptr->index = 17;
packet_ptr->seqno =4711;
packet_ptr->index = 17; // TODO: replace with sensible value
packet_ptr->seqno =4711; // TODO: replace with sensible value
prrt_packet_source_payload * payload = malloc(sizeof(prrt_packet_source_payload));
......@@ -62,40 +123,25 @@ int create_packet_source(prrt_packet *packet_ptr, uint8_t priority, const void *
return 0;
}
int encode_packet_source(void *buf, uint16_t buf_size, prrt_packet *packet) {
prrt_packet_source_payload * payload = packet->payload;
if(buf_size < packet->payload_len + PRRT_PACKET_GENERAL_HEADER_SIZE) {
return -1;
}
memcpy(buf, packet, PRRT_PACKET_GENERAL_HEADER_SIZE);
buf += PRRT_PACKET_GENERAL_HEADER_SIZE;
memcpy(buf, payload, PRRT_PACKET_SOURCE_HEADER_SIZE);
buf += PRRT_PACKET_SOURCE_HEADER_SIZE;
memcpy(buf, payload + PRRT_PACKET_SOURCE_HEADER_SIZE, packet->payload_len - PRRT_PACKET_SOURCE_HEADER_SIZE);
return 0;
}
int decode_packet_source(void *buf_ptr, uint16_t buf_size, prrt_packet *packet_ptr) {
uint32_t payload_len = (uint32_t) (buf_size - PRRT_PACKET_GENERAL_HEADER_SIZE);
packet_ptr->type_priority = *(uint8_t*) buf_ptr;
uint8_t* index_ptr = (uint8_t*) (buf_ptr+1);
packet_ptr->index = *index_ptr;
uint16_t* seqno_prt = (uint16_t*) (buf_ptr+2);
packet_ptr->seqno = *seqno_prt;
prrt_packet *create_packet_feedback(uint8_t priority, uint8_t index, uint16_t seqno, uint32_t round_trip_time,
uint32_t bandwidth, uint32_t burstiness_coefficient, uint32_t packet_loss_rate,
uint32_t feedback_block) {
prrt_packet *packet_ptr = malloc(sizeof(prrt_packet));
packet_ptr->type_priority = PACKET_TYPE_FEEDBACK << 4;
packet_ptr->type_priority |= priority & 0x0F;
packet_ptr->index = index;
packet_ptr->seqno = seqno;
if(packet_type(packet_ptr) != PACKET_TYPE_SOURCE) {
perror("DECODING A NON-SOURCE PACKET AS SOURCE.");
}
unsigned char* payload_buffer = malloc(payload_len);
memcpy(payload_buffer, buf_ptr + PRRT_PACKET_GENERAL_HEADER_SIZE, payload_len);
prrt_packet_feedback_payload * payload = malloc(sizeof(prrt_packet_feedback_payload));
packet_ptr->payload = payload_buffer;
packet_ptr->payload_len = payload_len;
payload->round_trip_time = round_trip_time;
payload->bandwidth = bandwidth;
payload->burstiness_coefficient = burstiness_coefficient;
payload->packet_loss_rate = packet_loss_rate;
payload->feedback_block = feedback_block;
printf("PACKET: \n");
print_packet(packet_ptr);
packet_ptr->payload = (void*) payload;
packet_ptr->payload_len = (uint32_t) (sizeof(prrt_packet_source_payload));
return 0;
}
return packet_ptr;
}
\ No newline at end of file
......@@ -20,23 +20,46 @@ typedef struct {
#define PRRT_PACKET_SOURCE_HEADER_SIZE 12
typedef struct {
uint32_t timestamp;
uint16_t rtt;
uint16_t round_trip_time;
uint16_t packet_timeout;
uint16_t decoding_timeout;
uint16_t feedback_timer;
} prrt_packet_source_payload;
# define PRRT_PACKET_FEEDBACK_SIZE 20
typedef struct {
uint32_t round_trip_time;
uint32_t packet_loss_rate;
uint32_t burstiness_coefficient;
uint32_t bandwidth;
uint32_t feedback_block;
} prrt_packet_feedback_payload;
uint8_t packet_type(prrt_packet *packet_ptr);
uint8_t packet_priority(prrt_packet *packet_ptr);
uint16_t packet_size(prrt_packet *packet_ptr);
int print_packet(prrt_packet *packet_ptr);
// CREATE: PRRT_PACKET
// ENCODE: PRRT_PACKET -> BYTES
// DECODE: BYTES -> PRRT_PACKET
// DELETE:
int decode_packet(void *buf_ptr, uint16_t buf_size, prrt_packet *packet_ptr);
int create_packet_source(prrt_packet *packet_ptr, uint8_t priority, const void * data_ptr, unsigned long data_len);
int encode_packet_source(void* buf_ptr, uint16_t buf_size, prrt_packet *packet_ptr);
int decode_packet_source(void* buf_ptr, uint16_t buf_size, prrt_packet *packet_ptr);
int encode_packet(void *buf_ptr, uint16_t buf_size, prrt_packet *packet_ptr);
int delete_packet(prrt_packet *packet_ptr);
int create_packet_repetition(prrt_packet packet, uint8_t priority);
int create_packet_parity(prrt_packet packet, uint8_t priority);
int create_packet_feedback(prrt_packet packet, uint8_t priority);
prrt_packet *create_packet_feedback(uint8_t priority, uint8_t index, uint16_t seqno, uint32_t round_trip_time,
uint32_t bandwidth, uint32_t burstiness_coefficient, uint32_t packet_loss_rate,
uint32_t feedback_block);
int encode_packet_feedback(void *buf_ptr, uint16_t buf_size, prrt_packet *pkt_ptr);
int decode_packet_feedback(void* buf_ptr, uint16_t buf_size, prrt_packet *packet_ptr);
#endif //PRRT_FRAME_H
......@@ -60,18 +60,19 @@ int prrt_connect(prrt_socket *sock_ptr, char *host, uint16_t port) {
}
int prrt_send(prrt_socket *sock_ptr, const void *data, size_t data_len) {
prrt_packet * packet = malloc(sizeof(prrt_packet));
create_packet_source(packet, 5, data, data_len);
prrt_packet packet;
create_packet_source(&packet, 5, data, data_len);
// TODO: finally delete_packet(packet);
uint8_t buf[MAX_PAYLOAD_LENGTH];
uint32_t length = packet_size(packet);
if(encode_packet_source(buf, MAX_PAYLOAD_LENGTH, packet) < 0) {
uint32_t length = packet_size(&packet);
if(encode_packet(buf, MAX_PAYLOAD_LENGTH, &packet) < 0) {
perror("BUF too small.");
return -1;
}
print_packet(packet);
// SENDING TO ALL RECEIVERS
int i;
for(i = 0; i < sock_ptr->receiver_len; i++) {
prrt_receiver recv = sock_ptr->receivers[i];
......@@ -105,10 +106,9 @@ prrt_packet *prrt_recv(prrt_socket *sock_ptr) {
n = recvfrom(sock_ptr->fd_data, buffer, MAX_PAYLOAD_LENGTH, 0, (struct sockaddr *) &remote, &addrlen);
uint16_t remote_port = ntohs(remote.sin_port);
char *remote_host = inet_ntoa(remote.sin_addr);
printf("got a datagram from %s port %d\n", remote_host, remote_port);
prrt_packet *packet = malloc(sizeof(prrt_packet));
decode_packet_source(buffer, (uint16_t) n, packet);
decode_packet(buffer, (uint16_t) n, packet);
// REPLY
struct sockaddr_in targetaddr;
......@@ -121,11 +121,19 @@ prrt_packet *prrt_recv(prrt_socket *sock_ptr) {
hp = gethostbyname(remote_host);
memcpy((void *)&targetaddr.sin_addr, hp->h_addr_list[0], (size_t) hp->h_length);
if((sendto(sock_ptr->fd_data, buffer, (size_t) n, 0, (struct sockaddr *) &targetaddr, sizeof(targetaddr)) < 0)) {
perror("sendto failed");
return NULL;
prrt_packet* feedback_pkt_ptr = create_packet_feedback(0, 19, 4715, 5, 5, 47, 50, 1);
uint8_t buf[MAX_PAYLOAD_LENGTH];
uint32_t length = packet_size(feedback_pkt_ptr);
if(encode_packet(buf, MAX_PAYLOAD_LENGTH, feedback_pkt_ptr) < 0) {
perror("BUF too small.");
} else {
if((sendto(sock_ptr->fd_feedback, buf, length, 0, (struct sockaddr *) &targetaddr, sizeof(targetaddr)) < 0)) {
perror("sendto failed");
return NULL;
}
}
return packet;
}
......@@ -137,8 +145,7 @@ int prrt_close_socket(prrt_socket *sock_ptr) {
return 0;
}
ssize_t prrt_recv_feedback(prrt_socket *sock_ptr, void *bufin, size_t length) {
printf("RECEIVING FB");
prrt_packet * prrt_recv_feedback(prrt_socket *sock_ptr, void *bufin, size_t length) {
ssize_t n;
struct sockaddr_in remote;
socklen_t addrlen = sizeof(remote);
......@@ -146,7 +153,9 @@ ssize_t prrt_recv_feedback(prrt_socket *sock_ptr, void *bufin, size_t length) {
n = recvfrom(sock_ptr->fd_feedback, bufin, length, 0, (struct sockaddr *) &remote, &addrlen);
uint16_t remote_port = ntohs(remote.sin_port);
char *remote_host = inet_ntoa(remote.sin_addr);
printf("got feedback from %s port %d\n", remote_host, remote_port);
printf("RECV FEEDBACK: %s:%d\n", remote_host, remote_port);
return n;
prrt_packet * packet_ptr = malloc(sizeof(prrt_packet));
decode_packet(bufin, (uint16_t) n, packet_ptr);
return packet_ptr;
}
......@@ -29,6 +29,6 @@ int prrt_close_socket(prrt_socket *sock_ptr);
int prrt_connect(prrt_socket *sock_ptr, char *host, uint16_t port);
int prrt_send(prrt_socket *sock_ptr, const void *data, size_t data_len);
prrt_packet *prrt_recv(prrt_socket *sock_ptr);
ssize_t prrt_recv_feedback(prrt_socket *sock_ptr, void *bufin, size_t length);
prrt_packet * prrt_recv_feedback(prrt_socket *sock_ptr, void *bufin, size_t length);
#endif // PRRT_SOCKET_H
......@@ -29,24 +29,16 @@ int main(int argc, char* const argv) {
printf("SENDING\n");
char *message = "this is a message";
size_t msg_len = strlen(message);
int i;
for(i = 0; i < msg_len; i++) {
if(i % 4 == 0) {
printf("|");
}
printf("%2x", message[i]);
}
printf("\n");
prrt_send(&sock, message, msg_len);
prrt_send(&sock, message, strlen(message));
char bufin[MAXBUF];
ssize_t t = prrt_recv_feedback(&sock, bufin, MAXBUF);
printf("FEEDBACK: %d\n", (int) t);
prrt_packet *t = prrt_recv_feedback(&sock, bufin, MAXBUF);
//print_packet(t);
delete_packet(t);
t = prrt_recv_feedback(&sock, bufin, MAXBUF);
printf("FEEDBACK: %d\n", (int) t);
//print_packet(t);
delete_packet(t);
prrt_close_socket(&sock);
return 0;
......
......@@ -3,9 +3,9 @@
#include <stdlib.h>
#include "prrt/packet.h"
#include "defines.h"
#include "util/common.h"
int main() {
int i;
char *message = "this is a message";
prrt_packet * packet = malloc(sizeof(prrt_packet));
......@@ -13,27 +13,13 @@ int main() {
print_packet(packet);
uint8_t buf[MAX_PAYLOAD_LENGTH];
char buf[MAX_PAYLOAD_LENGTH];
uint16_t length = packet_size(packet);
if(encode_packet_source(buf, MAX_PAYLOAD_LENGTH, packet) < 0) {
if(encode_packet(buf, MAX_PAYLOAD_LENGTH, packet) < 0) {
perror("BUF too small.");
return -1;
}
for(i = 0; i < length; i++) {
if(i % 4 == 0) {
printf("|");
}
printf("%2x", buf[i]);
}
printf("\n");
prrt_packet * packet2 = malloc(sizeof(prrt_packet));
decode_packet_source(buf, length, packet2);
print_buffer(buf, length);
return 0;
}
\ No newline at end of file
#include <stdio.h>
#include "common.h"
int print_buffer(char* buf, int length) {
int i;
for(i = 0; i < length; i++) {
if(i % 4 == 0) {
printf("|");
}
printf("%2x", buf[i]);
}
printf("\n");
}
\ No newline at end of file
#ifndef PRRT_COMMON_H
#define PRRT_COMMON_H
int print_buffer(char* buf, int length);
#endif //PRRT_COMMON_H
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment