`
刘亚鑫
  • 浏览: 18268 次
社区版块
存档分类
最新评论

android下如何设置系统时间

 
阅读更多

 

       最近做项目涉及到了怎么设置系统时间,起初觉得这个问题是很简单的,但是事实并非如此,在这个问题上卡壳了好几天。

       试了好几种方法,总算有了一定的成果。

 

1:

第一反应是查看android setting的源码(packages\apps\Settings),因为系统-日期和时间里面有能够设置时间的选项。

 

在其DateTimeSettings里面发现了它是利用 Calendar和系统类SystemClock来进行设置时间,我依样画葫芦,却提示Unable to open alarm driver。

 

百度了下,对于这个问题众说缤纷,有说是缺少权限配置文件,有说是通过把应用改为系统应用,来达到使用这个api的目的。把应用改为系统应用肯定不能满足我的需求,于是我又去试了下前面的方法,我在配置文件里面增加了这个权限。

        

  <uses-permission android:name="android.permission.WRITE_SETTINGS" />

 

 

结果依然提示我 Unable to open alarm driver。

 

2:

因为我的应用允许Root,所以我第二反应是想到利用linux命令来进行设置系统时间。但是我试了好几种方法,

 

系统时间虽然可以设置,但是却出现了时间不准确,甚至系统崩溃重启的情况。

 

 

Runtime.getRuntime().exec("su");
RootTools.sendShell("date -s 20130409 \n",10);
RootTools.sendShell("date -s 1311420409637 \n",10);

 

    

3:

搜遍了所有的中文android论坛,对于这个问题的解决方法都是千篇一律,后来总算在stackoverflow上面找到了答案。

给出的解决方法有二种,一种是修改系统的/dev/alarm文件,一种是直接利用date -s 命令。

 

方法一:

 public void setTime(long time) {
    if (ShellInterface.isSuAvailable()) {
      ShellInterface.runCommand("chmod 666 /dev/alarm");
      SystemClock.setCurrentTimeMillis(time);
      ShellInterface.runCommand("chmod 664 /dev/alarm");
    }
  }

/**
 * Interface to the Superuser shell on Android devices with some helper functions.<p/><p/>
 * Common usage for su shell:<p/>
 * <code>if(ShellInterface.isSuAvailable()) { ShellInterface.runCommand("reboot"); }</code>
 * <p/><p/>
 * To get process output as a String:<p/>
 * <code>if(ShellInterface.isSuAvailable()) { String date = ShellInterface.getProcessOutput("date"); }</code>
 * <p/><p/>
 * To run command with standard shell (no root permissions):
 * <code>ShellInterface.setShell("sh");</code><p/>
 * <code>ShellInterface.runCommand("date");</code>
 * <p/><p/>
 * Date: Mar 24, 2010
 * Time: 4:14:07 PM
 *
 * @author serge
 */
public class ShellInterface {
  private static final String TAG = "ShellInterface";

  private static String shell;

  // uid=0(root) gid=0(root)
  private static final Pattern UID_PATTERN = Pattern.compile("^uid=(\\d+).*?");

  enum OUTPUT {
    STDOUT,
    STDERR,
    BOTH
  }

  private static final String EXIT = "exit\n";

  private static final String[] SU_COMMANDS = new String[]{
    "su",
    "/system/xbin/su",
    "/system/bin/su"
  };

  private static final String[] TEST_COMMANDS = new String[]{
    "id",
    "/system/xbin/id",
    "/system/bin/id"
  };

  public static synchronized boolean isSuAvailable() {
    if (shell == null) {
      checkSu();
    }
    return shell != null;
  }

  public static synchronized void setShell(String shell) {
    ShellInterface.shell = shell;
  }

  private static boolean checkSu() {
    for (String command : SU_COMMANDS) {
      shell = command;
      if (isRootUid()) return true;
    }
    shell = null;
    return false;
  }

  private static boolean isRootUid() {
    String out = null;
    for (String command : TEST_COMMANDS) {
      out = getProcessOutput(command);
      if (out != null && out.length() > 0) break;
    }
    if (out == null || out.length() == 0) return false;
    Matcher matcher = UID_PATTERN.matcher(out);
    if (matcher.matches()) {
      if ("0".equals(matcher.group(1))) {
        return true;
      }
    }
    return false;
  }

  public static String getProcessOutput(String command) {
    try {
      return _runCommand(command, OUTPUT.STDERR);
    } catch (IOException ignored) {
      return null;
    }
  }

  public static boolean runCommand(String command) {
    try {
      _runCommand(command, OUTPUT.BOTH);
      return true;
    } catch (IOException ignored) {
      return false;
    }
  }

  private static String _runCommand(String command, OUTPUT o) throws IOException {
    DataOutputStream os = null;
    Process process = null;
    try {
      process = Runtime.getRuntime().exec(shell);
      os = new DataOutputStream(process.getOutputStream());
      InputStreamHandler sh = sinkProcessOutput(process, o);
      os.writeBytes(command + '\n');
      os.flush();
      os.writeBytes(EXIT);
      os.flush();
      process.waitFor();
      if (sh != null) {
        String output = sh.getOutput();
        Log.d(TAG, command + " output: " + output);
        return output;
      } else {
        return null;
      }
    } catch (Exception e) {
      final String msg = e.getMessage();
      Log.e(TAG, "runCommand error: " + msg);
      throw new IOException(msg);
    } finally {
      try {
        if (os != null) {
          os.close();
        }
        if (process != null) {
          process.destroy();
        }
      } catch (Exception ignored) {}
    }
  }

  public static InputStreamHandler sinkProcessOutput(Process p, OUTPUT o) {
    InputStreamHandler output = null;
    switch (o) {
      case STDOUT:
        output = new InputStreamHandler(p.getErrorStream(), false);
        new InputStreamHandler(p.getInputStream(), true);
        break;
      case STDERR:
        output = new InputStreamHandler(p.getInputStream(), false);
        new InputStreamHandler(p.getErrorStream(), true);
        break;
      case BOTH:
        new InputStreamHandler(p.getInputStream(), true);
        new InputStreamHandler(p.getErrorStream(), true);
        break;
    }
    return output;
  }

  private static class InputStreamHandler extends Thread {
    private final InputStream stream;
    private final boolean     sink;
    StringBuffer output;

    public String getOutput() {
      return output.toString();
    }

    InputStreamHandler(InputStream stream, boolean sink) {
      this.sink = sink;
      this.stream = stream;
      start();
    }

    @Override
    public void run() {
      try {
        if (sink) {
          while (stream.read() != -1) {}
        } else {
          output = new StringBuffer();
          BufferedReader b = new BufferedReader(new InputStreamReader(stream));
          String s;
          while ((s = b.readLine()) != null) {
            output.append(s);
          }
        }
      } catch (IOException ignored) {}
    }
  }
}

 

 

方法二:

public void setDate()
    {
        try {
            Process process = Runtime.getRuntime().exec("su");
        DataOutputStream os = new DataOutputStream(process.getOutputStream());
            os.writeBytes("date -s 20120419.024012; \n");
        } catch (Exception e) {
            Log.d(TAG,"error=="+e.toString());
            e.printStackTrace();
        }
    } 

 

总结:出现了这种问题,归根究底在于我自己的知识积累不够,对于linux命令熟悉度不高,应当多加强多接触这方面的知识,弥补不足。

 

 

   

 

 

 

 

 

分享到:
评论
1 楼 ygswine 2014-01-04  
很是感谢, 你的博文对我很有用. 谢谢

相关推荐

Global site tag (gtag.js) - Google Analytics