Add getmtu and setmtu interface commands
Bug: 9372485
Change-Id: I0dfa6b1f973426d67f976a9c79be8de90e3d9c19
Signed-off-by: Dmitry Shmidt <dimitrysh@google.com>
diff --git a/CommandListener.cpp b/CommandListener.cpp
index 3002da6..40d3637 100644
--- a/CommandListener.cpp
+++ b/CommandListener.cpp
@@ -522,6 +522,31 @@
"Failed to change IPv6 state", true);
}
return 0;
+ } else if (!strcmp(argv[1], "getmtu")) {
+ char *msg = NULL;
+ int mtu = 0;
+ if (sInterfaceCtrl->getMtu(argv[2], &mtu) == 0) {
+ asprintf(&msg, "MTU = %d", mtu);
+ cli->sendMsg(ResponseCode::InterfaceGetMtuResult, msg, false);
+ free(msg);
+ } else {
+ cli->sendMsg(ResponseCode::OperationFailed,
+ "Failed to get MTU", true);
+ }
+ return 0;
+ } else if (!strcmp(argv[1], "setmtu")) {
+ if (argc != 4) {
+ cli->sendMsg(ResponseCode::CommandSyntaxError,
+ "Usage: interface setmtu <interface> <val>", false);
+ return 0;
+ }
+ if (sInterfaceCtrl->setMtu(argv[2], argv[3]) == 0) {
+ cli->sendMsg(ResponseCode::CommandOkay, "MTU changed", false);
+ } else {
+ cli->sendMsg(ResponseCode::OperationFailed,
+ "Failed to get MTU", true);
+ }
+ return 0;
} else {
cli->sendMsg(ResponseCode::CommandSyntaxError, "Unknown interface cmd", false);
return 0;
diff --git a/InterfaceController.cpp b/InterfaceController.cpp
index 0d8f121..c305be9 100644
--- a/InterfaceController.cpp
+++ b/InterfaceController.cpp
@@ -46,6 +46,8 @@
const char ipv6_proc_path[] = "/proc/sys/net/ipv6/conf";
+const char sys_net_path[] = "/sys/class/net";
+
InterfaceController::InterfaceController()
: sendCommand_(NULL) {
// Initial IPv6 settings.
@@ -163,3 +165,26 @@
closedir(dir);
return 0;
}
+
+int InterfaceController::getMtu(const char *interface, int *mtu)
+{
+ char buf[16];
+ int size = sizeof(buf);
+ char *path;
+ asprintf(&path, "%s/%s/mtu", sys_net_path, interface);
+ int success = readFile(path, buf, &size);
+ if (!success && mtu)
+ *mtu = atoi(buf);
+ free(path);
+ return success;
+
+}
+
+int InterfaceController::setMtu(const char *interface, const char *mtu)
+{
+ char *path;
+ asprintf(&path, "%s/%s/mtu", sys_net_path, interface);
+ int success = writeFile(path, mtu, strlen(mtu));
+ free(path);
+ return success;
+}
diff --git a/InterfaceController.h b/InterfaceController.h
index 5943a9a..b8bbc92 100644
--- a/InterfaceController.h
+++ b/InterfaceController.h
@@ -35,6 +35,8 @@
int interfaceCommand(int argc, char *argv[], char **rbuf);
int setEnableIPv6(const char *interface, const int on);
int setIPv6PrivacyExtensions(const char *interface, const int on);
+ int getMtu(const char *interface, int *mtu);
+ int setMtu(const char *interface, const char *mtu);
private:
void *libh_;
diff --git a/NetdConstants.cpp b/NetdConstants.cpp
index 1ab09a5..c3c16eb 100644
--- a/NetdConstants.cpp
+++ b/NetdConstants.cpp
@@ -122,3 +122,24 @@
close(fd);
return 0;
}
+
+int readFile(const char *path, char *buf, int *sizep)
+{
+ int fd = open(path, O_RDONLY);
+ int size;
+
+ if (fd < 0) {
+ ALOGE("Failed to open %s: %s", path, strerror(errno));
+ return -1;
+ }
+
+ size = read(fd, buf, *sizep);
+ if (size < 0) {
+ ALOGE("Failed to write %s: %s", path, strerror(errno));
+ close(fd);
+ return -1;
+ }
+ *sizep = size;
+ close(fd);
+ return 0;
+}
diff --git a/NetdConstants.h b/NetdConstants.h
index eb59af2..d686968 100644
--- a/NetdConstants.h
+++ b/NetdConstants.h
@@ -34,6 +34,7 @@
int execIptables(IptablesTarget target, ...);
int execIptablesSilently(IptablesTarget target, ...);
int writeFile(const char *path, const char *value, int size);
+int readFile(const char *path, char *buf, int *sizep);
#define ARRAY_SIZE(a) (sizeof(a) / sizeof(*(a)))
diff --git a/ResponseCode.h b/ResponseCode.h
index 7689ef8..85f183a 100644
--- a/ResponseCode.h
+++ b/ResponseCode.h
@@ -45,6 +45,7 @@
static const int TetheringStatsResult = 221;
static const int DnsProxyQueryResult = 222;
static const int ClatdStatusResult = 223;
+ static const int InterfaceGetMtuResult = 224;
// 400 series - The command was accepted but the requested action
// did not take place.