2015-12-22 13 views
13

Ho un BroadcastReceiver che riceve input da una fonte esterna.Risultati diversi imprevisti dallo stesso input di stringa

Questo ricevitore deve quindi comportarsi come un programma "simile a un mouse" e inviare eventi di input al sistema. Ho accesso e permessi di root.

mio problema è che quando invio una stringa come "input tap 275 410", il programma si comporta in modo corretto, se ho anche dividere la stringa come "input" + " tap" + " 275" + " 410", funziona ancora ...

Tuttavia, quando monto la stringa come la desiderata:

"input " + CursorSystem.command + " " + coords[0] + " " + coords[1]

Poi non succede nulla ... durante il debug, tutte le stringhe guardato sono esattamente gli stessi (meno la posizione):

value = {char[26]@830031306976} 0 = 'i' 105 1 = 'n' 110 2 = 'p' 112 3 = 'u' 117 4 = 't' 116 5 = ' ' 32 6 = 't' 116 7 = 'a' 97 8 = 'p' 112 9 = ' ' 32 10 = '2' 50 11 = '7' 55 12 = '5' 53 13 = ' ' 32 14 = '4' 52 15 = '1' 49 16 = '0' 48 17 = '\u0000' 0 18 = '\u0000' 0 19 = '\u0000' 0 20 = '\u0000' 0 21 = '\u0000' 0 22 = '\u0000' 0 23 = '\u0000' 0 24 = '\u0000' 0 25 = '\u0000' 0 

Vorrei una guida o una proprietà da studiare, poiché i miei risultati non sono efficaci. Per quanto posso dire, questo non è un problema di autorizzazione, né è un problema di thread, dal momento che i registri mostrano la richiesta di autorizzazione (e la concessione), un thread per la vita fino a quando il ricevitore viene eseguito (ma se io eseguire il debug per troppo tempo, allora viene ucciso dopo un po '[30 + secondi])

Il Receiver.onReceive:

public void onReceive(Context context, Intent intent) { 
    String command = intent.getStringExtra("command"); 
    String touch = intent.getStringExtra("touch"); 
    if (Executor.isRootAvailable()) { 
     Executor executor = new Executor(); 
     ArrayList<String> commands = new ArrayList<>(); 
     if (command != null) { 
      if (command.length() > 0) { 
       if (commands.add("input " + command)) { 
        executor.execute(commands); 
       } 
      } 
     } else if (touch != null) { 
      if (CursorSystem.isAlive) { // Always true for the executions 
       CursorSystem.doInput(); 
       if (CursorSystem.state == CursorSystem.STATE) { // Always true for the executions 
        int[] coords = CursorSystem.coordinates; 
        if (coords != null) { 
// This line is where (I guess) that the problem lies. 
// CursorSystem.command is "tap", coords[0] and coords[1] is the result of (a view).getLocationOnScreen(coordinates) 
// It results in a 2 positions int array with (x, y) coordinates, these values are always correct. 
         if (commands.add("input " + CursorSystem.command + " " + coords[0] + " " + coords[1])) { 
          executor.execute(commands); 
          CursorSystem.doInput(); 
         } else { 
          // error... 
         } 
        } else { 
         // error... 
        } 
       } else { 
        // error... 
       } 
      } else { 
       error... 
      } 
     } else { 
      error... 
     } 
    } else { 
     error... 
    } 
} 

L'Executor.execute:

public final boolean execute(ArrayList<String> commands) { 
    boolean resp = false; 
    try { 
     if (commands != null && commands.size() > 0) { 
      Process suProcess = Runtime.getRuntime().exec("su"); 
      DataOutputStream dataOutputStream = new DataOutputStream(suProcess.getOutputStream()); 
      for (String currCommand : commands) { 
       dataOutputStream.writeBytes(currCommand); 
       dataOutputStream.writeBytes("\n"); 
       dataOutputStream.flush(); 
      } 
      dataOutputStream.writeBytes("exit\n"); 
      dataOutputStream.flush(); 
      try { 
       int suProcessRetval = suProcess.waitFor(); 
       return (suProcessRetval != 255); // Always yields 0 
      } catch (Exception ex) { 
       // errors... 
      } 
     } else { 
      // error... 
     } 
    } catch (IOException ex) { 
     Log.w(TAG, "IOException: ", ex); 
    } catch (SecurityException ex) { 
     Log.w(TAG, "SecurityException: ", ex); 
    } catch (Exception ex) { 
     Log.w(TAG, "Generic Exception: ", ex); 
    } 
    return resp; 
} 
+0

In 'Executor.execute', si restituisce 'resp' che sarà sempre falso poiché non lo si cambia da nessuna parte. È così che dovrebbe essere? –

+0

Puoi anche indicare cosa è esattamente la classe 'CursorSystem' e formattare la riga' value' se può essere? Immagino che 'CursorSystem' sia la tua classe.Sarà utile vedere il suo codice completo. –

+0

@AkashAggarwal Sì, principalmente perché il codice ora è un casino di recensioni. Il codice alla fine raggiungerà 'return (suProcessRetval! = 255);' che valuta true ... Inoltre, la classe 'CursorSystem' ha oltre duemila righe di codice. Le variabili principali utilizzate sono sempre impostate (mai nulle almeno), 'CursorSystem.isAlive' è un' booleano' sempre debugato come 'true', la maggior parte degli altri codici mostrati sono in realtà diversi e sono stati semplificati per la domanda ... Allo stesso tempo, non compaiono errori di LogCat, non vengono lanciati "Exception", nessun errore ... e nessuna risposta. – Bonatti

risposta

3

Per chiunque sia interessato:

Il problema trovato era che le CursorSystem ImageViews utilizzati, che ha aiutato l'utente a "target" ciò che l'interazione è stata voluta (e dove). Durante l'esecuzione, il comando può essere ricevuto e l'immagine può essere spostata nel punto in cui si verifica il comando, quindi "ricevendo" l'evento.

aggiungendo le seguenti bandiere:

.LayoutParams.FLAG_NOT_FOCUSABLE 
.LayoutParams.FLAG_NOT_TOUCHABLE 
.LayoutParams.FLAG_LAYOUT_NO_LIMITS 

ammessi al sistema di non prendere in considerazione le viste come interactable, così come "disegnare" loro al di fuori dai limiti, in modo che l'utente potrebbe "magnetiche" il dispositivo menu nascosti , così come fare clic su un target che potenzialmente potrebbe NON esistere. Ciò ha causato alcuni programmi "Launcher" per intercettare MotionEvent e non fare nulla.

Il comando è stato eseguito correttamente, solo nessun risultato è stato visualizzato e ci ha indotto a interpretarlo come "non fare nulla".

-1

sostituire

if (commands.add("input " + CursorSystem.command + " " + coords[0] + " " + coords[1])) { 
          executor.execute(commands); 
          CursorSystem.doInput(); 
         } 

con

String newCommand = "input " + CursorSystem.command + " " + coords[0] + " " + coords[1]; 
newCommand = newCommand.replace("\u0000", "").replace("\\u0000", "");// removes NUL chars and backslash+u0000 
if(commands.add(newCommand)){ 
    executor.execute(commands); 
    CursorSystem.doInput(); 
    } 
+0

Sebbene questo possa rispondere alla domanda dell'OP, la pubblicazione di blocchi di codice solido senza alcuna spiegazione non ha alcuno scopo educativo. Si prega di migliorare la risposta spiegando perché questo codice è una soluzione o se si basa su OP cosa è cambiato e per quale motivo. –

+0

Ho commentato la mia riga di codice: "// rimuove i caratteri NUL e il backslash + u0000" non è sufficiente? –

+0

@LinhNguyen Come indicato nella domanda, l'argomento String è uguale. Non ci sono caratteri nulli o caratteri indesiderati (come backlash, nuova riga, avanzamento riga, ecc.). Il problema non sembra rientrare nel codice, poiché la "correzione" fornita all'applicazione non ha modificato né il Servizio né la classe al suo interno. Valore – Bonatti

Problemi correlati