-
Notifications
You must be signed in to change notification settings - Fork 0
/
comms_manager.c
137 lines (111 loc) · 3.51 KB
/
comms_manager.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
#include "comms_manager.h"
#include "applibs/remotex.h"
static bool initialized = false;
static int sock_fd;
static uint8_t receive_buffer[5 * 1024];
bool create_socket(void)
{
struct sockaddr_in server;
int retry_count = 0;
int connect_status = -1;
#ifndef AZURE_SPHERE_REMOTEX_IP
printf("No AZURE_SPHERE_REMOTEX_IP variable defined in root CMakeLists.txt\n");
printf("Add the following to CMakeLists.txt\n");
printf("add_compile_definitions(AZURE_SPHERE_REMOTEX_IP = \"xxx.xxx.xxx.xxx\"\n");
return false;
#endif
if (initialized)
{
return true;
}
sock_fd = socket(AF_INET, SOCK_STREAM, 0);
if (sock_fd == -1)
{
printf("Could not create a socket for an Azure Sphere RemoteX connection\n");
}
#ifdef AZURE_SPHERE_REMOTEX_IP
server.sin_addr.s_addr = inet_addr(AZURE_SPHERE_REMOTEX_IP);
server.sin_family = AF_INET;
server.sin_port = htons(8888);
#endif
while (retry_count < 10)
{
#ifdef AZURE_SPHERE_REMOTEX_IP
printf("Attempting connection to Azure Sphere RemoteX on IP address %s...\n", AZURE_SPHERE_REMOTEX_IP);
#endif
if ((connect_status = connect(sock_fd, (struct sockaddr *)&server, sizeof(server))) < 0)
{
printf("Connection to Azure Sphere RemoteX failed\n");
printf("Retrying in 5 seconds\n");
nanosleep(&(struct timespec){5, 0}, NULL);
retry_count++;
}
else
{
break;
}
}
if (connect_status < 0)
{
printf("Connection to Azure Sphere RemoteX failed\n");
return false;
}
struct timeval tv;
tv.tv_sec = 360;
tv.tv_usec = 0;
setsockopt(sock_fd, SOL_SOCKET, SO_RCVTIMEO, (const char *)&tv, sizeof tv);
initialized = true;
printf("\nConnected to Azure Sphere RemoteX.\n");
char platform_information[128];
RemoteX_PlatformInformation(platform_information, sizeof(platform_information));
printf("%s\n\n", platform_information);
return true;
}
ssize_t socket_send_msg(void *msg, uint8_t command, size_t request_length, size_t response_length, bool respond)
{
size_t bytes_received = 0;
if (!create_socket())
{
return -1;
}
CTX_HEADER *header = (CTX_HEADER *)msg;
header->block_length = (uint16_t)request_length;
header->cmd = command;
header->contract_version = REMOTEX_CONTRACT_VERSION;
header->response_length = response_length;
#ifdef AZURE_SPHERE_REMOTEX_PERFORMANCE_MODE
header->respond = respond;
#else
header->respond = true;
#endif
if (send(sock_fd, msg, request_length, 0) != (ssize_t)request_length)
{
// puts("Send to Azure Sphere RemoteX failed\n");
return -1;
}
if (!header->respond)
{
return response_length;
}
while (bytes_received < response_length)
{
ssize_t byte_count = recv(sock_fd, receive_buffer + bytes_received, response_length - bytes_received, 0);
if (byte_count > 0)
{
bytes_received += byte_count;
}
else if (byte_count < 0)
{
break;
}
}
if (bytes_received > 0 && ((CTX_HEADER *)receive_buffer)->contract_version < REMOTEX_CONTRACT_VERSION)
{
printf("AzureSphereRemoteX.Service is running with an out of date contact definition. Update RemoteX.Service with the latest contract.h and redeploy to Azure Sphere.\n");
}
if (bytes_received <= response_length)
{
memcpy(msg, receive_buffer, bytes_received);
}
return bytes_received;
}