in source/linux/network.c [145:268]
int get_net_connections_from_proc_buf(
struct aws_array_list *net_conns,
struct aws_allocator *allocator,
struct aws_byte_cursor *proc_net_data,
const struct aws_iotdevice_network_ifconfig *ifconfig,
enum aws_iotdevice_network_protocol protocol) {
AWS_PRECONDITION(net_conns != NULL);
AWS_PRECONDITION(allocator != NULL);
AWS_PRECONDITION(ifconfig != NULL);
AWS_PRECONDITION(aws_byte_cursor_is_valid(proc_net_data));
int return_value = AWS_OP_SUCCESS;
struct aws_array_list lines;
AWS_ZERO_STRUCT(lines);
aws_array_list_init_dynamic(&lines, allocator, 10, sizeof(struct aws_byte_cursor));
aws_byte_cursor_split_on_char(proc_net_data, '\n', &lines);
/* first line is header text info */
aws_array_list_pop_front_n(&lines, 1);
/* last line is empty */
aws_array_list_pop_back(&lines);
struct aws_byte_cursor line;
struct aws_iotdevice_metric_net_connection *connection = NULL;
while (AWS_OP_SUCCESS == aws_array_list_front(&lines, &line)) {
aws_array_list_pop_front(&lines);
char local_addr_h[9];
char local_port_h[6];
char remote_addr_h[9];
char remote_port_h[6];
char state_h[3];
int tokens_read = sscanf(
(const char *)line.ptr,
"%*s %8s %*c %4s %8s %*c %4s %2s %*s",
local_addr_h,
local_port_h,
remote_addr_h,
remote_port_h,
state_h);
if (tokens_read != EXPECTED_NETWORK_CONFIG_TOKENS) {
AWS_LOGF_WARN(AWS_LS_IOTDEVICE_NETWORK_CONFIG, "id=%p: Bad line in /proc/net/*** file", (void *)ifconfig);
continue;
}
uint16_t state = strtol(state_h, NULL, 16);
if (state == LINUX_NCS_ESTABLISHED || state == LINUX_NCS_LISTEN) {
connection = aws_mem_calloc(allocator, 1, sizeof(struct aws_iotdevice_metric_net_connection));
if (connection == NULL) {
return_value = AWS_OP_ERR;
AWS_LOGF_ERROR(
AWS_LS_IOTDEVICE_NETWORK_CONFIG,
"id=%p: Could not allocate memory for network connection",
(void *)ifconfig);
goto cleanup;
}
AWS_ZERO_STRUCT(*connection);
char local_addr[IPV4_ADDRESS_SIZE];
char remote_addr[IPV4_ADDRESS_SIZE];
s_hex_addr_to_ip_str(local_addr, IPV4_ADDRESS_SIZE, local_addr_h);
s_hex_addr_to_ip_str(remote_addr, IPV4_ADDRESS_SIZE, remote_addr_h);
connection->local_port = strtol(local_port_h, NULL, 16);
connection->remote_port = strtol(remote_port_h, NULL, 16);
connection->state = map_network_state(strtol(state_h, NULL, 16));
struct aws_hash_element *element;
int return_code = aws_hash_table_find(&ifconfig->iface_name_to_info, local_addr, &element);
if (element == NULL || return_code != AWS_OP_SUCCESS) {
AWS_LOGF_WARN(
AWS_LS_IOTDEVICE_NETWORK_CONFIG,
"id=%p: Could not retrieve interface mapping for address: %s",
(void *)ifconfig,
local_addr);
aws_mem_release(allocator, connection);
connection = NULL;
continue;
}
struct aws_iotdevice_network_iface *iface = (struct aws_iotdevice_network_iface *)element->value;
connection->local_interface = aws_string_new_from_c_str(allocator, iface->iface_name);
if (!connection->local_interface) {
return_value = AWS_OP_ERR;
AWS_LOGF_ERROR(
AWS_LS_IOTDEVICE_NETWORK_CONFIG,
"id=%p: Could not allocate memory for connection local address",
(void *)ifconfig);
goto cleanup;
}
connection->remote_address = aws_string_new_from_c_str(allocator, remote_addr);
if (!connection->remote_address) {
return_value = AWS_OP_ERR;
AWS_LOGF_ERROR(
AWS_LS_IOTDEVICE_NETWORK_CONFIG,
"id=%p: Could not allocate memory for connection remote address",
(void *)ifconfig);
goto cleanup;
}
connection->protocol = protocol;
if (AWS_OP_SUCCESS != aws_array_list_push_back(net_conns, connection)) {
goto cleanup;
} else {
aws_mem_release(allocator, connection);
connection = NULL;
}
}
}
cleanup:
if (connection != NULL) {
aws_string_destroy(connection->local_interface);
aws_string_destroy(connection->remote_address);
aws_mem_release(allocator, connection);
}
aws_array_list_clean_up(&lines);
return return_value;
}