Skip to content

Commit 0e08bf8

Browse files
committed
Code clean up and look for credentials every 10 seconds.
1 parent e945e9c commit 0e08bf8

4 files changed

Lines changed: 92 additions & 32 deletions

File tree

CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -75,6 +75,7 @@ add_library(bm_sbc_core STATIC
7575
src/core/runtime.cpp
7676
src/core/app_runner.cpp
7777
src/core/pcap_file_sink.cpp
78+
src/core/safe_cmd.cpp
7879
src/platform/linux/platform_linux.cpp
7980
src/net/virtual_port_device.cpp
8081
src/net/gateway_device.cpp

apps/gateway/app_main.cpp

Lines changed: 33 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -14,19 +14,17 @@ extern "C" {
1414
#include "gateway_device.h"
1515
#include "gateway_ipc.h"
1616
#include "runtime.h"
17+
#include "safe_cmd.h"
1718
#include <arpa/inet.h>
1819
#include <atomic>
1920
#include <cstdio>
2021
#include <cstdlib>
2122
#include <cstring>
2223
#include <errno.h>
2324
#include <filesystem>
24-
#include <string>
2525
#include <sys/socket.h>
26-
#include <sys/wait.h>
2726
#include <time.h>
2827
#include <unistd.h>
29-
#include <vector>
3028

3129
using namespace std::filesystem;
3230

@@ -596,27 +594,6 @@ static void get_wifi_enable(void) {
596594

597595
static const std::string connection_name = "user-wifi";
598596

599-
static int run(const std::vector<const char *> &args) {
600-
// Prevent command injection from system() by utilizing execvp
601-
std::vector<char *> argv;
602-
for (auto *a : args) {
603-
argv.push_back(const_cast<char *>(a));
604-
}
605-
argv.push_back(nullptr);
606-
607-
pid_t pid = fork();
608-
if (pid < 0)
609-
return -1;
610-
if (pid == 0) {
611-
execvp(args[0], argv.data());
612-
_exit(127);
613-
}
614-
int status = 0;
615-
if (waitpid(pid, &status, 0) < 0)
616-
return -1;
617-
return WIFEXITED(status) ? WEXITSTATUS(status) : -1;
618-
}
619-
620597
static bool copy_connections(void) {
621598
static const path connection_location =
622599
"/etc/NetworkManager/system-connections/";
@@ -714,17 +691,18 @@ static BmErr set_wifi_credential(std::string &cred, uint8_t *payload) {
714691
}
715692

716693
// If both SSID and password are available create a new network manager
717-
// connection.
694+
// connection
718695
if (CONTEXT.wifi_password.size() && CONTEXT.wifi_ssid.size()) {
719696

720697
bm_log_info("Saving wifi credentials...");
721698

722699
// Remove any existing wifi credentials and then add the new one
723-
run({"nmcli", "connection", "delete", connection_name.c_str()});
724-
int ret = run({"nmcli", "connection", "add", "type", "wifi", "ifname",
725-
"wlan0", "con-name", connection_name.c_str(), "ssid",
726-
CONTEXT.wifi_ssid.c_str(), "wifi-sec.key-mgmt", "wpa-psk",
727-
"wifi-sec.psk", CONTEXT.wifi_password.c_str()});
700+
std::string cmd = "nmcli connection delete " + connection_name;
701+
safe_cmd(cmd.c_str());
702+
cmd = "nmcli connection add type wifi ifname wlan0 con-name " +
703+
connection_name + " ssid " + CONTEXT.wifi_ssid +
704+
" wifi-sec.key-mgmt wpa-psk wifi-sec.psk " + CONTEXT.wifi_password;
705+
int ret = safe_cmd(cmd.c_str());
728706
if (ret != 0) {
729707
bm_log_error("Could not save wifi credentials, err: %d", ret);
730708
return BmEBADMSG;
@@ -756,7 +734,9 @@ static BmErr wifi_password_cb(uint8_t *payload) {
756734
return set_wifi_credential(CONTEXT.wifi_password, payload);
757735
}
758736

759-
static void get_wifi_credentials(void) {
737+
static void get_wifi_credentials(BmTimer timer = nullptr) {
738+
(void)timer;
739+
760740
bm_log_debug("Ticks before bcmp config get in %s: %u", __func__,
761741
bm_get_tick_count());
762742
BmErr err = BmOK;
@@ -766,6 +746,27 @@ static void get_wifi_credentials(void) {
766746
WIFI_PASS_KEY_LEN, WIFI_PASS_KEY, &err, wifi_password_cb);
767747
}
768748

749+
static void start_wifi_credentials_timer(void) {
750+
static BmTimer timer = nullptr;
751+
752+
if (timer) {
753+
return;
754+
}
755+
756+
// See if credentials are there to begin with
757+
get_wifi_credentials();
758+
759+
// Check for credentials every timer_ms
760+
static constexpr uint32_t timer_ms = 10000;
761+
static constexpr uint32_t timer_wait_ms = 10;
762+
timer = bm_timer_create("creds", timer_ms, true, NULL, get_wifi_credentials);
763+
if (!timer) {
764+
return;
765+
}
766+
767+
bm_timer_start(timer, timer_wait_ms);
768+
}
769+
769770
#define MAX_NMEA_RMC_LEN 82
770771
#define MAX_NMEA_FIELDS 14
771772

@@ -1022,7 +1023,7 @@ void setup(void) {
10221023
get_mote_system_configs();
10231024
get_sbc_command();
10241025
get_wifi_enable();
1025-
get_wifi_credentials();
1026+
start_wifi_credentials_timer();
10261027
gateway_ipc_init(CONTEXT.mote_node_id);
10271028
}
10281029

src/core/safe_cmd.cpp

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
#include "safe_cmd.h"
2+
#include <stdio.h>
3+
#include <string.h>
4+
#include <sys/wait.h>
5+
#include <unistd.h>
6+
#include <vector>
7+
8+
/*!
9+
@brief Prevent command injection with a safe system call
10+
11+
@details Uses execvp instead of system to prevent command injection from
12+
calls that have exposure to the outside world.
13+
14+
@param cmd command string to run
15+
16+
@return 0 on success
17+
other on failure
18+
*/
19+
int safe_cmd(const char *cmd) {
20+
std::vector<char *> argv;
21+
22+
// Copy string to local variable
23+
size_t cmd_len = strlen(cmd) + 1;
24+
char *local = static_cast<char *>(malloc(cmd_len));
25+
if (!local) {
26+
return -1;
27+
}
28+
strncpy(local, cmd, cmd_len);
29+
30+
char *token = strtok(local, " ");
31+
while (token) {
32+
argv.push_back(token);
33+
token = strtok(NULL, " ");
34+
}
35+
argv.push_back(nullptr);
36+
37+
free(local);
38+
39+
pid_t pid = fork();
40+
if (pid < 0) {
41+
return -1;
42+
}
43+
if (pid == 0) {
44+
execvp(argv[0], argv.data());
45+
_exit(127);
46+
}
47+
int status = 0;
48+
if (waitpid(pid, &status, 0) < 0) {
49+
return -1;
50+
}
51+
return WIFEXITED(status) ? WEXITSTATUS(status) : -1;
52+
}

src/core/safe_cmd.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
#ifndef __SAFE_CMD_H__
2+
#define __SAFE_CMD_H__
3+
4+
int safe_cmd(const char *cmd);
5+
6+
#endif

0 commit comments

Comments
 (0)