add radio_state set/query support
[project/umbim.git] / cli.c
diff --git a/cli.c b/cli.c
index cb107b7..1dd6330 100644 (file)
--- a/cli.c
+++ b/cli.c
@@ -216,8 +216,9 @@ static int
 mbim_config_response(void *buffer, int len)
 {
        struct mbim_basic_connect_ip_configuration_r *ip = (struct mbim_basic_connect_ip_configuration_r *) buffer;
-       char ipv4[16];
+       char out[40];
        int i;
+       uint32_t offset;
 
        if (len < sizeof(struct mbim_basic_connect_ip_configuration_r)) {
                fprintf(stderr, "message not long enough\n");
@@ -226,23 +227,54 @@ mbim_config_response(void *buffer, int len)
 
        if (le32toh(ip->ipv4configurationavailable) & MBIM_IP_CONFIGURATION_AVAILABLE_FLAG_ADDRESS)
                for (i = 0; i < le32toh(ip->ipv4addresscount); i++) {
-                       mbim_get_ipv4(buffer, ipv4, ip->ipv4address + (i * 4));
-                       printf("  ipv4address: %s\n", ipv4);
+                       offset = le32toh(ip->ipv4address) + (i * 4);
+                       mbim_get_ipv4(buffer, out, 4 + offset);
+                       printf("  ipv4address: %s/%d\n", out, mbim_get_int(buffer, offset));
                }
        if (le32toh(ip->ipv4configurationavailable) & MBIM_IP_CONFIGURATION_AVAILABLE_FLAG_DNS) {
-               mbim_get_ipv4(buffer, ipv4, ip->ipv4gateway);
-               printf("  ipv4gateway: %s\n", ipv4);
+               mbim_get_ipv4(buffer, out, le32toh(ip->ipv4gateway));
+               printf("  ipv4gateway: %s\n", out);
        }
        if (le32toh(ip->ipv4configurationavailable) & MBIM_IP_CONFIGURATION_AVAILABLE_FLAG_MTU)
                printf("  ipv4mtu: %d\n", le32toh(ip->ipv4mtu));
        if (le32toh(ip->ipv4configurationavailable) & MBIM_IP_CONFIGURATION_AVAILABLE_FLAG_DNS)
                for (i = 0; i < le32toh(ip->ipv4dnsservercount); i++) {
-                       mbim_get_ipv4(buffer, ipv4, ip->ipv4dnsserver + (i * 4));
-                       printf("  ipv4dnsserver: %s\n", ipv4);
+                       mbim_get_ipv4(buffer, out, le32toh(ip->ipv4dnsserver) + (i * 4));
+                       printf("  ipv4dnsserver: %s\n", out);
                }
 
-       printf("  ipv6configurationavailable: %04X\n", le32toh(ip->ipv6configurationavailable));
+       if (le32toh(ip->ipv6configurationavailable) & MBIM_IP_CONFIGURATION_AVAILABLE_FLAG_ADDRESS)
+               for (i = 0; i < le32toh(ip->ipv6addresscount); i++) {
+                       offset = le32toh(ip->ipv6address) + (i * 16);
+                       mbim_get_ipv6(buffer, out, 4 + offset);
+                       printf("  ipv6address: %s/%d\n", out, mbim_get_int(buffer, offset));
+               }
+       if (le32toh(ip->ipv6configurationavailable) & MBIM_IP_CONFIGURATION_AVAILABLE_FLAG_DNS) {
+               mbim_get_ipv6(buffer, out, le32toh(ip->ipv6gateway));
+               printf("  ipv6gateway: %s\n", out);
+       }
+       if (le32toh(ip->ipv6configurationavailable) & MBIM_IP_CONFIGURATION_AVAILABLE_FLAG_MTU)
+               printf("  ipv6mtu: %d\n", le32toh(ip->ipv6mtu));
+       if (le32toh(ip->ipv6configurationavailable) & MBIM_IP_CONFIGURATION_AVAILABLE_FLAG_DNS)
+               for (i = 0; i < le32toh(ip->ipv6dnsservercount); i++) {
+                       mbim_get_ipv6(buffer, out, le32toh(ip->ipv6dnsserver) + (i * 16));
+                       printf("  ipv6dnsserver: %s\n", out);
+               }
+
+       return 0;
+}
 
+static int
+mbim_radio_response(void *buffer, int len)
+{
+       struct mbim_basic_connect_radio_state_r *r = (struct mbim_basic_connect_radio_state_r *) buffer;
+
+       if (len < sizeof(struct mbim_basic_connect_radio_state_r)) {
+               fprintf(stderr, "message not long enough\n");
+               return -1;
+       }
+       printf("  hwradiostate: %s\n", r->hwradiostate ? "on" : "off");
+       printf("  swradiostate: %s\n", r->swradiostate ? "on" : "off");
        return 0;
 }
 
@@ -306,6 +338,7 @@ mbim_detach_request(void)
 static int
 mbim_connect_request(void)
 {
+       char *apn;
        struct mbim_basic_connect_connect_s *c =
                (struct mbim_basic_connect_connect_s *) mbim_setup_command_msg(basic_connect,
                        MBIM_MESSAGE_COMMAND_TYPE_SET, MBIM_CMD_BASIC_CONNECT_CONNECT,
@@ -314,8 +347,22 @@ mbim_connect_request(void)
        c->activationcommand = htole32(MBIM_ACTIVATION_COMMAND_ACTIVATE);
        c->iptype = htole32(MBIM_CONTEXT_IP_TYPE_DEFAULT);
        memcpy(c->contexttype, uuid_context_type_internet, 16);
-       if (_argc > 0)
-               mbim_encode_string(&c->accessstring, *_argv);
+       if (_argc > 0) {
+               apn = index(*_argv, ':');
+               if (!apn) {
+                       apn = *_argv;
+               } else {
+                       apn[0] = 0;
+                       apn++;
+                       if (!strcmp(*_argv, "ipv4"))
+                               c->iptype = htole32(MBIM_CONTEXT_IP_TYPE_IPV4);
+                       else if (!strcmp(*_argv, "ipv6"))
+                               c->iptype = htole32(MBIM_CONTEXT_IP_TYPE_IPV6);
+                       else if (!strcmp(*_argv, "ipv4v6"))
+                               c->iptype = htole32(MBIM_CONTEXT_IP_TYPE_IPV4V6);
+               }
+               mbim_encode_string(&c->accessstring, apn);
+       }
        if (_argc > 3) {
                if (!strcmp(_argv[1], "pap"))
                        c->authprotocol = htole32(MBIM_AUTH_PROTOCOL_PAP);
@@ -397,6 +444,27 @@ mbim_config_request(void)
        return mbim_send_command_msg();
 }
 
+static int
+mbim_radio_request(void)
+{
+       if (_argc > 0) {
+               struct mbim_basic_connect_radio_state_s *rs =
+                       (struct mbim_basic_connect_radio_state_s *) mbim_setup_command_msg(basic_connect,
+                               MBIM_MESSAGE_COMMAND_TYPE_SET, MBIM_CMD_BASIC_CONNECT_RADIO_STATE,
+                               sizeof(struct mbim_basic_connect_radio_state_r));
+
+               if (!strcmp(_argv[0], "off"))
+                       rs->radiostate = htole32(MBIM_RADIO_SWITCH_STATE_OFF);
+               else
+                       rs->radiostate = htole32(MBIM_RADIO_SWITCH_STATE_ON);
+       } else {
+               mbim_setup_command_msg(basic_connect,
+                       MBIM_MESSAGE_COMMAND_TYPE_QUERY, MBIM_CMD_BASIC_CONNECT_RADIO_STATE,
+                       sizeof(struct mbim_basic_connect_radio_state_r));
+       }
+       return mbim_send_command_msg();
+}
+
 static struct mbim_handler handlers[] = {
        { "caps", 0, mbim_device_caps_request, mbim_device_caps_response },
        { "pinstate", 0, mbim_pin_state_request, mbim_pin_state_response },
@@ -408,12 +476,13 @@ static struct mbim_handler handlers[] = {
        { "connect", 0, mbim_connect_request, mbim_connect_response },
        { "disconnect", 0, mbim_disconnect_request, mbim_connect_response },
        { "config", 0, mbim_config_request, mbim_config_response },
+       { "radio", 0, mbim_radio_request, mbim_radio_response },
 };
 
 static int
 usage(void)
 {
-       fprintf(stderr, "Usage: mbim <caps|pinstate|unlock|connect|disconnect> [options]\n"
+       fprintf(stderr, "Usage: umbim <caps|pinstate|unlock|registration|subscriber|attach|detach|connect|disconnect|config|radio> [options]\n"
                "Options:\n"
                "    -d <device>        the device (/dev/cdc-wdmX)\n"
                "    -t <transaction>   the transaction id\n"