要触发 Shell 脚本的自定义设置
Custom Settings to Fire off Shell Script
所以,我正在为我的 android phone 开发一个 "custom settings" 应用程序,我需要一点帮助....
这是我想做的...
我希望能够在 /res/xml/file.xml 中设置一个 Preference
,它会根据 xml 中的某个值触发 shell 脚本]
那么,假设我的 Preference
是:
<ListPreference android:key="dp_cleaner" android:title="My Cleaner" android:entries="@array/dp_cleaner_entries" android:entryValues="@array/dp_cleaner_entries_values" />
而启动 shell 脚本的 .smali
方法是
.method public static execRootCmdSilent(Ljava/lang/String;)I
# Contains all my code to fire it off...
.end method
用法
:try_start_0
const-string v2, "THE_COMMAND"
invoke-static {v2}, Lcom/android/settings/ExecSH;->execRootCmdSilent(Ljava/lang/String;)I
:try_end_0
.catch Ljava/lang/Exception; {:try_start_0 .. :try_end_0} :catch_0
如何从列表中点击的值填充我的 const-string
?我假设我需要通过 key
以某种方式 findPreference
,但我不知道如何将点击值传递给方法....
是否可以像这样简单:
.class public Lcom/android/settings/ExecSH;
.super Lcom/android/settings/SettingsPreferenceFragment;
.source "ExecSH.java"
.implements Landroid/preference/Preference$OnPreferenceChangeListener;
.implements Landroid/preference/Preference$OnPreferenceClickListener;
# direct methods
.method public onPreferenceTreeClick(Landroid/preference/PreferenceScreen;Landroid/preference/Preference;)Z
:try_start_0
const-string v2, Landroid/preference/Preference;->findPreference(Ljava/lang/CharSequence;)Landroid/preference/Preference;
invoke-static {v2}, Lcom/android/settings/ExecSH;->execRootCmdSilent(Ljava/lang/String;)I
:try_end_0
.catch Ljava/lang/Exception; {:try_start_0 .. :try_end_0} :catch_0
.end method
.method public static execRootCmdSilent(Ljava/lang/String;)I
#MY CODE
.end method
您的 class 需要实现 Preference.OnPreferenceChangedListener
接口并设置为您的 ListPreference
的更改侦听器。您的侦听器方法将作为参数传递新值,此时您可以将其传递给您的 execRootCmdSilent
方法。
关键的 smali 部分位于以下文件的底部:
.method public onPreferenceChange(Landroid/preference/Preference;Ljava/lang/Object;)Z
move-object v2, p2
// there are some more moves here and a test, which is why we're shuffling registers
move-object v3, v2
invoke-virtual {v3}, Ljava/lang/Object;->toString()Ljava/lang/String;
move-result-object v3
invoke-static {v3}, Lsarbs/com/tinker/SettingsActivity;->execRootCmdSilent(Ljava/lang/String;)I
基本上,p2
值是传递给 onPreferenceChange
方法的第二个参数 (newValue
)。我们将其移动到本地寄存器中,然后 invoke-virtual
toString
方法就可以了。将该调用的结果移动到 v3
寄存器中,然后您可以 invoke-static
您的 execRootCmdSilent
方法使用该 v3
寄存器作为参数。
我用来实现这个的 Java 代码:
package sarbs.com.tinker;
import android.os.Bundle;
import android.preference.ListPreference;
import android.preference.Preference;
import android.preference.PreferenceActivity;
public class SettingsActivity extends PreferenceActivity implements Preference.OnPreferenceChangeListener {
ListPreference mListPreference;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
addPreferencesFromResource(R.xml.pref_general);
mListPreference = (ListPreference) findPreference("dp_cleaner");
mListPreference.setOnPreferenceChangeListener(this);
}
@Override
public boolean onPreferenceChange(Preference preference, Object newValue) {
if (preference == mListPreference) {
execRootCmdSilent(newValue.toString());
}
return true;
}
public static int execRootCmdSilent(String str) {
return 0;
}
}
及其产生的smali代码:
.class public Lsarbs/com/tinker/SettingsActivity;
.super Landroid/preference/PreferenceActivity;
.source "SettingsActivity.java"
# interfaces
.implements Landroid/preference/Preference$OnPreferenceChangeListener;
# instance fields
.field mListPreference:Landroid/preference/ListPreference;
# direct methods
.method public constructor <init>()V
.registers 3
.prologue
.line 8
move-object v0, p0
.local v0, "this":Lsarbs/com/tinker/SettingsActivity;
move-object v1, v0
invoke-direct {v1}, Landroid/preference/PreferenceActivity;-><init>()V
return-void
.end method
.method public static execRootCmdSilent(Ljava/lang/String;)I
.registers 3
.prologue
.line 30
move-object v0, p0
.local v0, "str":Ljava/lang/String;
const/4 v1, 0x0
move v0, v1
.end local v0 # "str":Ljava/lang/String;
return v0
.end method
# virtual methods
.method protected onCreate(Landroid/os/Bundle;)V
.registers 7
.prologue
.line 13
move-object v0, p0
.local v0, "this":Lsarbs/com/tinker/SettingsActivity;
move-object v1, p1
.local v1, "savedInstanceState":Landroid/os/Bundle;
move-object v2, v0
move-object v3, v1
invoke-super {v2, v3}, Landroid/preference/PreferenceActivity;->onCreate(Landroid/os/Bundle;)V
.line 15
move-object v2, v0
const v3, 0x7f030001
invoke-virtual {v2, v3}, Lsarbs/com/tinker/SettingsActivity;->addPreferencesFromResource(I)V
.line 17
move-object v2, v0
move-object v3, v0
const-string v4, "dp_cleaner"
invoke-virtual {v3, v4}, Lsarbs/com/tinker/SettingsActivity;->findPreference(Ljava/lang/CharSequence;)Landroid/preference/Preference;
move-result-object v3
check-cast v3, Landroid/preference/ListPreference;
iput-object v3, v2, Lsarbs/com/tinker/SettingsActivity;->mListPreference:Landroid/preference/ListPreference;
.line 18
move-object v2, v0
iget-object v2, v2, Lsarbs/com/tinker/SettingsActivity;->mListPreference:Landroid/preference/ListPreference;
move-object v3, v0
invoke-virtual {v2, v3}, Landroid/preference/ListPreference;->setOnPreferenceChangeListener(Landroid/preference/Preference$OnPreferenceChangeListener;)V
.line 19
return-void
.end method
.method public onPreferenceChange(Landroid/preference/Preference;Ljava/lang/Object;)Z
.registers 8
.prologue
.line 23
move-object v0, p0
.local v0, "this":Lsarbs/com/tinker/SettingsActivity;
move-object v1, p1
.local v1, "preference":Landroid/preference/Preference;
move-object v2, p2
.local v2, "newValue":Ljava/lang/Object;
move-object v3, v1
move-object v4, v0
iget-object v4, v4, Lsarbs/com/tinker/SettingsActivity;->mListPreference:Landroid/preference/ListPreference;
if-ne v3, v4, :cond_12
.line 24
move-object v3, v2
invoke-virtual {v3}, Ljava/lang/Object;->toString()Ljava/lang/String;
move-result-object v3
invoke-static {v3}, Lsarbs/com/tinker/SettingsActivity;->execRootCmdSilent(Ljava/lang/String;)I
move-result v3
.line 26
:cond_12
const/4 v3, 0x1
move v0, v3
.end local v0 # "this":Lsarbs/com/tinker/SettingsActivity;
return v0
.end method
所以,我正在为我的 android phone 开发一个 "custom settings" 应用程序,我需要一点帮助....
这是我想做的...
我希望能够在 /res/xml/file.xml 中设置一个 Preference
,它会根据 xml 中的某个值触发 shell 脚本]
那么,假设我的 Preference
是:
<ListPreference android:key="dp_cleaner" android:title="My Cleaner" android:entries="@array/dp_cleaner_entries" android:entryValues="@array/dp_cleaner_entries_values" />
而启动 shell 脚本的 .smali
方法是
.method public static execRootCmdSilent(Ljava/lang/String;)I
# Contains all my code to fire it off...
.end method
用法
:try_start_0
const-string v2, "THE_COMMAND"
invoke-static {v2}, Lcom/android/settings/ExecSH;->execRootCmdSilent(Ljava/lang/String;)I
:try_end_0
.catch Ljava/lang/Exception; {:try_start_0 .. :try_end_0} :catch_0
如何从列表中点击的值填充我的 const-string
?我假设我需要通过 key
以某种方式 findPreference
,但我不知道如何将点击值传递给方法....
是否可以像这样简单:
.class public Lcom/android/settings/ExecSH;
.super Lcom/android/settings/SettingsPreferenceFragment;
.source "ExecSH.java"
.implements Landroid/preference/Preference$OnPreferenceChangeListener;
.implements Landroid/preference/Preference$OnPreferenceClickListener;
# direct methods
.method public onPreferenceTreeClick(Landroid/preference/PreferenceScreen;Landroid/preference/Preference;)Z
:try_start_0
const-string v2, Landroid/preference/Preference;->findPreference(Ljava/lang/CharSequence;)Landroid/preference/Preference;
invoke-static {v2}, Lcom/android/settings/ExecSH;->execRootCmdSilent(Ljava/lang/String;)I
:try_end_0
.catch Ljava/lang/Exception; {:try_start_0 .. :try_end_0} :catch_0
.end method
.method public static execRootCmdSilent(Ljava/lang/String;)I
#MY CODE
.end method
您的 class 需要实现 Preference.OnPreferenceChangedListener
接口并设置为您的 ListPreference
的更改侦听器。您的侦听器方法将作为参数传递新值,此时您可以将其传递给您的 execRootCmdSilent
方法。
关键的 smali 部分位于以下文件的底部:
.method public onPreferenceChange(Landroid/preference/Preference;Ljava/lang/Object;)Z
move-object v2, p2
// there are some more moves here and a test, which is why we're shuffling registers
move-object v3, v2
invoke-virtual {v3}, Ljava/lang/Object;->toString()Ljava/lang/String;
move-result-object v3
invoke-static {v3}, Lsarbs/com/tinker/SettingsActivity;->execRootCmdSilent(Ljava/lang/String;)I
基本上,p2
值是传递给 onPreferenceChange
方法的第二个参数 (newValue
)。我们将其移动到本地寄存器中,然后 invoke-virtual
toString
方法就可以了。将该调用的结果移动到 v3
寄存器中,然后您可以 invoke-static
您的 execRootCmdSilent
方法使用该 v3
寄存器作为参数。
我用来实现这个的 Java 代码:
package sarbs.com.tinker;
import android.os.Bundle;
import android.preference.ListPreference;
import android.preference.Preference;
import android.preference.PreferenceActivity;
public class SettingsActivity extends PreferenceActivity implements Preference.OnPreferenceChangeListener {
ListPreference mListPreference;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
addPreferencesFromResource(R.xml.pref_general);
mListPreference = (ListPreference) findPreference("dp_cleaner");
mListPreference.setOnPreferenceChangeListener(this);
}
@Override
public boolean onPreferenceChange(Preference preference, Object newValue) {
if (preference == mListPreference) {
execRootCmdSilent(newValue.toString());
}
return true;
}
public static int execRootCmdSilent(String str) {
return 0;
}
}
及其产生的smali代码:
.class public Lsarbs/com/tinker/SettingsActivity;
.super Landroid/preference/PreferenceActivity;
.source "SettingsActivity.java"
# interfaces
.implements Landroid/preference/Preference$OnPreferenceChangeListener;
# instance fields
.field mListPreference:Landroid/preference/ListPreference;
# direct methods
.method public constructor <init>()V
.registers 3
.prologue
.line 8
move-object v0, p0
.local v0, "this":Lsarbs/com/tinker/SettingsActivity;
move-object v1, v0
invoke-direct {v1}, Landroid/preference/PreferenceActivity;-><init>()V
return-void
.end method
.method public static execRootCmdSilent(Ljava/lang/String;)I
.registers 3
.prologue
.line 30
move-object v0, p0
.local v0, "str":Ljava/lang/String;
const/4 v1, 0x0
move v0, v1
.end local v0 # "str":Ljava/lang/String;
return v0
.end method
# virtual methods
.method protected onCreate(Landroid/os/Bundle;)V
.registers 7
.prologue
.line 13
move-object v0, p0
.local v0, "this":Lsarbs/com/tinker/SettingsActivity;
move-object v1, p1
.local v1, "savedInstanceState":Landroid/os/Bundle;
move-object v2, v0
move-object v3, v1
invoke-super {v2, v3}, Landroid/preference/PreferenceActivity;->onCreate(Landroid/os/Bundle;)V
.line 15
move-object v2, v0
const v3, 0x7f030001
invoke-virtual {v2, v3}, Lsarbs/com/tinker/SettingsActivity;->addPreferencesFromResource(I)V
.line 17
move-object v2, v0
move-object v3, v0
const-string v4, "dp_cleaner"
invoke-virtual {v3, v4}, Lsarbs/com/tinker/SettingsActivity;->findPreference(Ljava/lang/CharSequence;)Landroid/preference/Preference;
move-result-object v3
check-cast v3, Landroid/preference/ListPreference;
iput-object v3, v2, Lsarbs/com/tinker/SettingsActivity;->mListPreference:Landroid/preference/ListPreference;
.line 18
move-object v2, v0
iget-object v2, v2, Lsarbs/com/tinker/SettingsActivity;->mListPreference:Landroid/preference/ListPreference;
move-object v3, v0
invoke-virtual {v2, v3}, Landroid/preference/ListPreference;->setOnPreferenceChangeListener(Landroid/preference/Preference$OnPreferenceChangeListener;)V
.line 19
return-void
.end method
.method public onPreferenceChange(Landroid/preference/Preference;Ljava/lang/Object;)Z
.registers 8
.prologue
.line 23
move-object v0, p0
.local v0, "this":Lsarbs/com/tinker/SettingsActivity;
move-object v1, p1
.local v1, "preference":Landroid/preference/Preference;
move-object v2, p2
.local v2, "newValue":Ljava/lang/Object;
move-object v3, v1
move-object v4, v0
iget-object v4, v4, Lsarbs/com/tinker/SettingsActivity;->mListPreference:Landroid/preference/ListPreference;
if-ne v3, v4, :cond_12
.line 24
move-object v3, v2
invoke-virtual {v3}, Ljava/lang/Object;->toString()Ljava/lang/String;
move-result-object v3
invoke-static {v3}, Lsarbs/com/tinker/SettingsActivity;->execRootCmdSilent(Ljava/lang/String;)I
move-result v3
.line 26
:cond_12
const/4 v3, 0x1
move v0, v3
.end local v0 # "this":Lsarbs/com/tinker/SettingsActivity;
return v0
.end method