Commit 6b38de2b authored by spiiroin's avatar spiiroin

[android] Optionally force an USB function on bootup. JB#41747

On some devices enumeration fails on the 1st connect after bootup unless
android usb has already been set up for some function at least once.

Add --android-bootup-function option that can be used on such devices
to force usb-moded to program some function and then clear the function
list when usb-moded is executed during device bootup.
Signed-off-by: spiiroin's avatarSimo Piiroinen <simo.piiroinen@jollamobile.com>
parent c30c8359
......@@ -23,6 +23,7 @@
#include <stdio.h>
#include <glib.h>
#include "usb_moded.h"
#include "usb_moded-android.h"
#include "usb_moded-log.h"
#include "usb_moded-modesetting.h"
......@@ -84,11 +85,17 @@ void android_init_values(void)
{
gchar *text;
/* If the directory is not there, no point emitting warnings
* about every file that is not going to be there either. */
if( access("/sys/class/android_usb/android0", F_OK) != 0 )
{
goto EXIT;
}
/* Disable */
write_to_file("/sys/class/android_usb/android0/enable", "0");
/* Configure */
if( (text = get_android_serial()) )
{
write_to_file("/sys/class/android_usb/android0/iSerial", text);
......@@ -128,8 +135,22 @@ void android_init_values(void)
/* For rndis to be discovered correctly in M$ Windows (vista and later) */
write_to_file("/sys/class/android_usb/f_rndis/wceis", "1");
/* Make sure android_usb does not stay disabled in case usb moded
* has crashed / been killed in inconvenient time. */
/* Some devices can have enumeration issues due to incomplete
* configuration on the 1st connect after bootup. Briefly setting
* up for example mass_storage function can be utilized as a
* workaround in such cases. */
if(!init_done_p()) {
const char *function = get_android_bootup_function();
if(function) {
write_to_file("/sys/class/android_usb/android0/functions", function);
write_to_file("/sys/class/android_usb/android0/enable", "1");
write_to_file("/sys/class/android_usb/android0/enable", "0");
}
}
/* Clear functions and enable */
write_to_file("/sys/class/android_usb/android0/functions", "none");
write_to_file("/sys/class/android_usb/android0/enable", "1");
EXIT:
......
......@@ -92,6 +92,30 @@ static gboolean android_ignore_next_udev_disconnect_event = FALSE;
static gboolean systemd_notify = FALSE;
#endif
/** Optional android usb function to setup during bootup */
static gchar *android_bootup_function = 0;
/** Get android usb function to setup during bootup
*
* @returns function name, or NULL if no function was requested
*/
const char *get_android_bootup_function(void)
{
return android_bootup_function;
}
/** Set android usb function to setup during bootup
*
* @param function usb function name, or NULL
*/
void set_android_bootup_function(const char *function)
{
char *value = function ? g_strdup(function) : 0;
g_free(android_bootup_function);
android_bootup_function = value;
}
/** Default allowed cable detection delay
*
* To comply with USB standards, the delay should be
......@@ -879,6 +903,10 @@ static void usage(void)
" output version information and exit\n"
" -m, --max-cable-delay=<ms>\n"
" maximum delay before accepting cable connection\n"
" -b, --android-bootup-function=<function>\n"
" Setup given function during bootup. Might be required\n"
" on some devices to make enumeration work on the 1st\n"
" cable connect.\n"
"\n");
}
......@@ -1332,6 +1360,7 @@ int main(int argc, char* argv[])
{ "systemd", no_argument, 0, 'n' },
{ "version", no_argument, 0, 'v' },
{ "max-cable-delay", required_argument, 0, 'm' },
{ "android-bootup-function", required_argument, 0, 'b' },
{ 0, 0, 0, 0 }
};
......@@ -1343,7 +1372,7 @@ int main(int argc, char* argv[])
* - - - - - - - - - - - - - - - - - - - */
/* Parse the command-line options */
while ((opt = getopt_long(argc, argv, "aifsTlDdhrnvm:", options, &opt_idx)) != -1)
while ((opt = getopt_long(argc, argv, "aifsTlDdhrnvm:b:", options, &opt_idx)) != -1)
{
switch (opt)
{
......@@ -1397,6 +1426,10 @@ int main(int argc, char* argv[])
set_cable_connection_delay(strtol(optarg, 0, 0));
break;
case 'b':
set_android_bootup_function(optarg);
break;
default:
usage();
exit(0);
......@@ -1602,6 +1635,8 @@ EXIT:
# endif
#endif
set_android_bootup_function(0);
/* Must be done just before exit to make sure no more wakelocks
* are taken and left behind on exit path */
allow_suspend();
......
......@@ -108,4 +108,7 @@ bool init_done_p(void);
void set_init_done(bool reached);
void probe_init_done(void);
const char *get_android_bootup_function(void);
void set_android_bootup_function(const char *function);
#endif /* USB_MODED_H */
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment