Re: Slow File Copy from Windows to Linux using JCIFS 1.3.17
Michael B Allen <[email protected]> Thu, 8 May 2014 04:58:09 -0400
| Newsgroups | gmane.network.samba.java |
|---|---|
| Message-ID | <CAGMFw4jwWCzc0rHkVET=HebHxjze2Qk3rbRp7ya2ZcMC1wMx7Q@mail.gmail.com> |
On Tue, Apr 1, 2014 at 7:37 AM, Lim, Ludwig Isaac (Legacy System Archeaologist) <[email protected]> wrote: > Hi: > > > > I’m using JCIFS to programmatically copy batch of files from > Windows to Linux using JCIFS. After upgrading from v 1.2.9 to 1.3.17, the > performance turned very slow. A copy of 1.3 MB file using JCIFS v 1.2.9 > takes 2.4 seconds but for v 1.3.17 it takes 10.9 seconds (with the same > code). > > > > Adding –Djcifs.util.loglevel=3 to program invocation gave me > the following: > > > > jcifs.smb.SmbException: Failed to connect: americas/<ip> > > jcifs.util.transport.TransportException > > java.net.NoRouteToHostException: No route to host > > at java.net.PlainSocketImpl.socketConnect(Native Method) Hi Ludwig, This is almost certainly a name service problem. Meaning JCIFS is trying and failing to lookup the name but is eventually successful after retrying with a different method. The actual file copying part is probably quick. The best way to diagnose this sort of issue is to get a packet capture (do not post packet captures to the mailing list) and look at the timestamps of the various communication. Then you can either adjust the names used in your code or the name service properties (see Setting Name Resolution Properties page: http://jcifs.samba.org/src/docs/resolver.html) to give you the right behavior for your environment. But in practice you should just use jcifs.resolveOrder=DNS and always use fully qualified DNS hostnames in your code. Never use a short name with no domain. That will almost certainly lead to name service issues even if your host uses DNS search suffix. JCIFS does not use any DNS search suffix logic. We would have to implement a DNS client for that (which would not be an unreasonable thing to do actually). > My code is basically like this (with some parts removed): > > > > class Test > > { > > > > public static void main(String args[]) > > { > > final int BUFF_SIZE = 8 * 1024 ; > > jcifs.Config.setProperty("jcifs.resolveOrder", "DNS"); > > jcifs.Config.setProperty ("jcifs.util.loglevel","3"); > > > > NtlmPasswordAuthentication auth = new > NtlmPasswordAuthentication("americas", “…", "…"); > > SmbFile rmifile; > > try { > > rmifile = new SmbFile("..”,auth) ; > > } catch (Exception e) { > > System.out.println("Error : " + e.getMessage()); > > return; > > } > > > > File localfile = null; > > InputStream bis = null; > > OutputStream bos = null; > > String localpath = "/home/accos/jcifs"; > > String filename = rmifile.getName(); > > localfile = new File(localpath + File.separator + filename); > > byte[] buffer = new byte [BUFF_SIZE]; > > int bytesRead; > > try { > > bis = new SmbFileInputStream(rmifile); > > bos = new FileOutputStream(localfile); > > > > > > while ( (bytesRead = bis.read(buffer))>0 ) { > > System.out.print("ok\n"); > > bos.write(buffer,0,bytesRead); > > } > > } catch ( Exception e) { > > System.out.println("Unable to copy file from samba to local file > : " + e.getMessage()); > > } > > finally { > > try { > > bos.close(); > > bis.close(); > > } catch (IOException e) { > > } > > } > > > > } > > } > > > > The file was copied as I was able to see bunch of “OK”s The code looks fine. Just make sure you use hostnames that are qualified with the correct domain. > P.S. Seems that the code below doesn’t work > > jcifs.Config.setProperty ("jcifs.util.loglevel","3"); Yes, the LogStream instance is created in a static initializer so this particular property cannot be set after the JCIFS classes are loaded. Mike -- Michael B Allen Java Active Directory Integration http://www.ioplex.com/