Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

SSL Broken Pipe

Tags:

java

android

ssl

I make POST requests in my application and somtimes (if i have a huge amount of Post data), the following error occured:

avax.net.ssl.SSLException: Write error: ssl=0x2f0610: I/O error during system call, Broken pipe

while executing http.execute(httpost) in the code below. Does anybody know how to avoid this?

I tryed to use AndroidHttpClient, but can't find a valid way for basic auth And i tryed a HttpsUrlConnection, but get the same error.

    public static String makePOSTRequest(String s, List<NameValuePair> nvps,
        String encoding) {
        String ret = "";
        UsernamePasswordCredentials c = new UsernamePasswordCredentials("XXX", "YYY");
        BasicCredentialsProvider cP = new BasicCredentialsProvider();
        cP.setCredentials(AuthScope.ANY, c);

        HttpParams httpParams = new BasicHttpParams();
        int connection_Timeout = 5000;
        HttpConnectionParams.setConnectionTimeout(httpParams,
                connection_Timeout);
        HttpConnectionParams.setSoTimeout(httpParams, connection_Timeout);
        DefaultHttpClient http = new DefaultHttpClient(httpParams);
        http.setCredentialsProvider(cP);
        HttpResponse res;
        try {
            HttpPost httpost = new HttpPost(s);
            httpost.setEntity(new UrlEncodedFormEntity(nvps,
                    HTTP.DEFAULT_CONTENT_CHARSET));
            res = http.execute(httpost);
            InputStream is = res.getEntity().getContent();
            BufferedInputStream bis = new BufferedInputStream(is);
            ByteArrayBuffer baf = new ByteArrayBuffer(50);
            int current = 0;
            while ((current = bis.read()) != -1) {
                baf.append((byte) current);
            }
            res = null;
            httpost = null;
            ret = new String(baf.toByteArray(), encoding);
            break;
        } catch (ClientProtocolException e) {
            ret = e.getMessage();

        } catch (IOException e) {
            ret = e.getMessage();
        }
    return ret;
}

edit: The following code is used for uploading files, if I try to upload small files, the code works, but if the files get bigger, i receive the broken pipe error. Using a faster Internetconnection will increase the filesize, it seemed to be a problem withe the time until the server is resetting the connection.

public static boolean upload_image2(String url,
        List<NameValuePair> nameValuePairs, File file, String encoding) {
    boolean erg = false;

                    HttpParams httpParams = new BasicHttpParams();
            int connection_Timeout = 120000;

     HttpConnectionParams.setConnectionTimeout(httpParams,connection_Timeout);
       HttpConnectionParams.setSoTimeout(httpParams, connection_Timeout);
       http = new DefaultHttpClient(httpParams);
        HttpResponse res;
        UsernamePasswordCredentials c = new UsernamePasswordCredentials(username, password);
        BasicCredentialsProvider cP = new BasicCredentialsProvider();
        cP.setCredentials(AuthScope.ANY, c);


        try {
            HttpPost httpost = new HttpPost(url);

            MultipartEntity entity = new MultipartEntity(
                    HttpMultipartMode.STRICT);

            FileBody isb = new FileBody(file, "application/*");
            entity.addPart("File", isb);
            for (int index = 0; index < nameValuePairs.size(); index++) {
                ContentBody cb;
                // Normal string data
                cb = new StringBody(nameValuePairs.get(index).getValue(),
                        "", null);
                entity.addPart(nameValuePairs.get(index).getName(), cb);
            }

            httpost.setEntity(entity);

            res = http.execute(httpost);
            InputStream is = res.getEntity().getContent();
            BufferedInputStream bis = new BufferedInputStream(is);
            ByteArrayBuffer baf = new ByteArrayBuffer(50);
            int current = 0;
            while ((current = bis.read()) != -1) {
                baf.append((byte) current);
            }
            res = null;
            httpost = null;
            String ret = new String(baf.toByteArray(), encoding);
            LastError = ret;
            erg = true;
        } catch (ClientProtocolException e) {
            // TODO Auto-generated catch block
            LastError = e.getMessage();
            erg = false;
        } catch (IOException e) {
            // TODO Auto-generated catch block
            LastError = e.getMessage();
            erg = false;
        }
    return erg;
}
like image 511
2red13 Avatar asked Nov 08 '11 16:11

2red13


2 Answers

I've had the same problem using the DefaultHttpClient, well, using my own implementation of the httpclient to support https. Small files it was working fine and big files were failing time after time.

After reading this response I've changed to the HttpsURLConnection like the accepted answer suggests and also because it is recommended by android (http://android-developers.blogspot.pt/2011/09/androids-http-clients.html).

The problem stood. Turns out the issue was on the server, I've changed the configs from the PHP server before to accept bigger sizes, but I totally forgot to change the client_max_body_size of the nginx. After making that small change sending big files was working. Through both HttpsUrlConnections and DefaultHttpClient.

like image 171
Rui Santos Avatar answered Oct 04 '22 05:10

Rui Santos


I had got the same error. The problem is in the Android library where is use DefaultHttpClient has been around since Android API level 1 and AndroidHttpClient has been available since Android API level 8. This is bug in android https://code.google.com/p/android/issues/detail?id=8625

My problem was: The default timeout is 60 seconds. When I ran the connection in the Wireshark. It was created handshake and he has been waiting on the ApplicationData, but he didn't get it so after timeout send FIN and I have got :javax.net.ssl.SSLException: Write error: ssl=0x2f0610: I/O error during system call, Broken pipe.

I resolved my problem problem setting timeout the http connection on the 5 minutes or something value is longer than 60second. If I can recommended how resolve your problem run on the server Wireshark and listening the comunication with mobile device.

like image 39
horkavlna Avatar answered Oct 04 '22 05:10

horkavlna