2015-09-17 100 views
1

我正在编写一个示例Android应用程序,它将创建一个简单的http服务器,但遇到一个小问题。Android ServerSocket接受权限被拒绝

这里是我的MainActivity

public class MainActivity extends Activity { 

    private ServerSocket ss; 

    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.activity_main); 
     Init(); 
    } 

    private void Init() { 
     Button btnStart = (Button) findViewById(R.id.btn_start); 

     btnStart.setOnClickListener(new View.OnClickListener() { 
      @Override 
      public void onClick(View v) { 
       new Thread(new Runnable() { 
        @Override 
        public void run() { 
         try{ 
          if(ss != null){ 
           return; 
          } 

          ss = new ServerSocket(8080); 

          while (true) { 
           Socket s = ss.accept(); 
           System.err.println("Client accepted"); 
           new Thread(new SocketProcessor(s)).start(); 
          } 
         } catch (Throwable throwable) { 
          throwable.printStackTrace(); 
         } 
        } 
       }).start(); 
      } 
     }); 
    } 
} 

而这里的SocketProcessor类

public class SocketProcessor implements Runnable { 

    private Socket s; 
    private InputStream is; 
    private OutputStream os; 

    public SocketProcessor(Socket s) throws Throwable { 
     this.s = s; 
     this.is = s.getInputStream(); 
     this.os = s.getOutputStream(); 
    } 

    public void run() { 
     try { 
      readInputHeaders(); 
      writeResponse("<html><body><h1>Hello world!</h1></body></html>"); 
     } catch (Throwable t) { 
       /*do nothing*/ 
     } finally { 
      try { 
       s.close(); 
      } catch (Throwable t) { 
        /*do nothing*/ 
      } 
     } 
     System.err.println("Client processing finished"); 
    } 

    private void writeResponse(String s) throws Throwable { 
     String response = "HTTP/1.1 200 OK\r\n" + 
       "Server: YarServer/2009-09-09\r\n" + 
       "Content-Type: text/html\r\n" + 
       "Content-Length: " + s.length() + "\r\n" + 
       "Connection: close\r\n\r\n"; 
     String result = response + s; 
     os.write(result.getBytes()); 
     os.flush(); 
    } 

    private void readInputHeaders() throws Throwable { 
     BufferedReader br = new BufferedReader(new InputStreamReader(is)); 
     while (true) { 
      String s = br.readLine(); 
      if (s == null || s.trim().length() == 0) { 
       break; 
      } 
     } 
    } 
} 

的问题是它给了我一个异常说拒绝的权限,但我确实有权限在我的清单

<?xml version="1.0" encoding="utf-8"?> 
<manifest xmlns:android="http://schemas.android.com/apk/res/android" 
    package="com.mainserver.myapplication"> 

    <uses-permission android:name="ANDROID.PERMISSION.INTERNET" /> 

    <application 
     android:allowBackup="true" 
     android:icon="@mipmap/ic_launcher" 
     android:label="@string/app_name" 
     android:theme="@style/AppTheme"> 

     <activity 
      android:name=".MainActivity" 
      android:label="@string/app_name"> 
      <intent-filter> 
       <action android:name="android.intent.action.MAIN" /> 

       <category android:name="android.intent.category.LAUNCHER" /> 
      </intent-filter> 
     </activity> 
    </application> 


</manifest> 

有什么问题的权限,我想念克什么?

在此先感谢。

这里是我的例外

09-17 17:01:11.072 12667-12842/com.mainserver.myapplication W/System.err﹕ java.net.SocketException: socket failed: EACCES (Permission denied) 
09-17 17:01:11.072 12667-12842/com.mainserver.myapplication W/System.err﹕ at libcore.io.IoBridge.socket(IoBridge.java:660) 
09-17 17:01:11.072 12667-12842/com.mainserver.myapplication W/System.err﹕ at java.net.PlainSocketImpl.create(PlainSocketImpl.java:198) 
09-17 17:01:11.072 12667-12842/com.mainserver.myapplication W/System.err﹕ at java.net.PlainServerSocketImpl.create(PlainServerSocketImpl.java:38) 
09-17 17:01:11.072 12667-12842/com.mainserver.myapplication W/System.err﹕ at java.net.ServerSocket.<init>(ServerSocket.java:103) 
09-17 17:01:11.072 12667-12842/com.mainserver.myapplication W/System.err﹕ at java.net.ServerSocket.<init>(ServerSocket.java:74) 
09-17 17:01:11.072 12667-12842/com.mainserver.myapplication W/System.err﹕ at com.mainserver.myapplication.MainActivity$1$1.run(MainActivity.java:37) 
09-17 17:01:11.072 12667-12842/com.mainserver.myapplication W/System.err﹕ at java.lang.Thread.run(Thread.java:818) 
09-17 17:01:11.072 12667-12842/com.mainserver.myapplication W/System.err﹕ Caused by: android.system.ErrnoException: socket failed: EACCES (Permission denied) 
09-17 17:01:11.072 12667-12842/com.mainserver.myapplication W/System.err﹕ at libcore.io.Posix.socket(Native Method) 
09-17 17:01:11.072 12667-12842/com.mainserver.myapplication W/System.err﹕ at libcore.io.BlockGuardOs.socket(BlockGuardOs.java:282) 
09-17 17:01:11.072 12667-12842/com.mainserver.myapplication W/System.err﹕ at libcore.io.IoBridge.socket(IoBridge.java:645) 
09-17 17:01:11.072 12667-12842/com.mainserver.myapplication W/System.err﹕ ... 6 more 
+0

很难相信它是由'accept()发出的''发布堆栈跟踪。将其编辑到您的问题中。 – EJP

+0

我想你在主线程中调用'accept'。只是扩展线程不会使start()的主体在另一个线程上执行。您应该实现Runnable,并将其提供给Thread实例以避免这种混淆。 – Fildor

+0

刚刚看到,你不仅在主线程中调用accept,还因为在click()中调用start()中的while(true),所以你完全阻止它在无限循环中,这会以“Unresponsive应用程序“无论如何。 – Fildor

回答

7

的堆栈跟踪你声明所需要的权限改为:

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

我想你应该创建一个新的类,套接字和现在一样关闭的唯一方法是关闭应用程序本身,也许它应该在异步任务中运行。

+0

这不是问题的答案。这些事情应该发表评论。 – Fildor