2009-03-03 3 views
1

직렬 포트에서 파일을 받고 싶습니다.이 X 모뎀 프로토콜은 Java의 직렬 포트를 통해 파일을 수신하도록 설계되었습니다. 그래서 누군가가 다음 plz에 대한 아이디어를 가질 수 있다면 저를 도와주세요. 나는 많은 문제에 봉착 해있다. plzJava에서 X 모뎀 프로토콜 구현

답변

1

SerialIO은 상업적으로 구현되어있다.

+0

나는 코드를 개발해야합니다. API가 있습니까? –

1

음 ... 그냥 the specs을 읽고 구현하십시오. 일반적으로 자바의 바이트 레벨을 훑어 보는 것은 어색 할 수 있지만 너무 어렵지는 않습니다.

기존 구현에 대해 많이 검색하지는 않았지만, 보통은 kgiannakakis에서 제안한 상업용 이상의 것보다 많습니다. :) 그렇지 않으면 아마도 한 걸음 뒤로 물러서서 Java (라이센스 허용, 물론)에서보고 다시 구현할 C 소스를 얻으십시오.

4

여기 있습니다.

나는 이것을 JModem source에서 발견했습니다. 데이터를 쓰는 위치를 보면 SOH, 블록 넘버, ~ 블록 넘버, 데이터 및 체크섬을 수행하는 것을 볼 수 있습니다. 128의 섹터 크기를 사용합니다. 함께 표준 XModem protocol을 구성합니다. XModem1K, YModem 및 ZModem을 여기에서 할 정도로 간단합니다.

/** 
* a tiny version of Ward Christensen's MODEM program for UNIX. 
* Written ~ 1980 by Andrew Scott Beals. Last revised 1982. 
* A.D. 2000 - dragged from the archives for use in Java Cookbook. 
* 
* @author C version by Andrew Scott Beals, sjobrg.andy%[email protected] 
* @author Java version by Ian F. Darwin, [email protected] 
* $Id: TModem.java,v 1.8 2000/03/02 03:40:50 ian Exp $ 
*/ 
class TModem { 

    protected final byte CPMEOF = 26;  /* control/z */ 
    protected final int MAXERRORS = 10;  /* max times to retry one block */ 
    protected final int SECSIZE = 128;  /* cpm sector, transmission block */ 
    protected final int SENTIMOUT = 30;  /* timeout time in send */ 
    protected final int SLEEP = 30;  /* timeout time in recv */ 

    /* Protocol characters used */ 

    protected final byte SOH = 1; /* Start Of Header */ 
    protected final byte EOT = 4; /* End Of Transmission */ 
    protected final byte ACK = 6; /* ACKnowlege */ 
    protected final byte NAK = 0x15; /* Negative AcKnowlege */ 

    protected InputStream inStream; 
    protected OutputStream outStream; 
    protected PrintWriter errStream; 

    /** Construct a TModem */ 
    public TModem(InputStream is, OutputStream os, PrintWriter errs) { 
     inStream = is; 
     outStream = os; 
     errStream = errs; 
    } 

    /** Construct a TModem with default files (stdin and stdout). */ 
    public TModem() { 
     inStream = System.in; 
     outStream = System.out; 
     errStream = new PrintWriter(System.err); 
    } 

    /** A main program, for direct invocation. */ 
    public static void main(String[] argv) throws 
     IOException, InterruptedException { 

     /* argc must == 2, i.e., `java TModem -s filename' */ 
     if (argv.length != 2) 
      usage(); 

     if (argv[0].charAt(0) != '-') 
      usage(); 

     TModem tm = new TModem(); 
     tm.setStandalone(true); 

     boolean OK = false; 
     switch (argv[0].charAt(1)){ 
     case 'r': 
      OK = tm.receive(argv[1]); 
      break; 
     case 's': 
      OK = tm.send(argv[1]); 
      break; 
     default: 
      usage(); 
     } 
     System.out.print(OK?"Done OK":"Failed"); 
     System.exit(0); 
    } 

    /* give user minimal usage message */ 
    protected static void usage() 
    { 
     System.err.println("usage: TModem -r/-s file"); 
     // not errStream, not die(), since this is static. 
     System.exit(1); 
    } 

    /** If we're in a standalone app it is OK to System.exit() */ 
    protected boolean standalone = false; 
    public void setStandalone(boolean is) { 
     standalone = is; 
    } 
    public boolean isStandalone() { 
     return standalone; 
    } 

    /** A flag used to communicate with inner class IOTimer */ 
    protected boolean gotChar; 

    /** An inner class to provide a read timeout for alarms. */ 
    class IOTimer extends Thread { 
     String message; 
     long milliseconds; 

     /** Construct an IO Timer */ 
     IOTimer(long sec, String mesg) { 
      milliseconds = 1000 * sec; 
      message = mesg; 
     } 

     public void run() { 
      try { 
      Thread.sleep(milliseconds); 
      } catch (InterruptedException e) { 
      // can't happen 
      } 
      /** Implement the timer */ 
      if (!gotChar) 
      errStream.println("Timed out waiting for " + message); 
      die(1); 
     } 
    } 

    /* 
    * send a file to the remote 
    */ 
    public boolean send(String tfile) throws IOException, InterruptedException 
    { 
     char checksum, index, blocknumber, errorcount; 
     byte character; 
     byte[] sector = new byte[SECSIZE]; 
     int nbytes; 
     DataInputStream foo; 

     foo = new DataInputStream(new FileInputStream(tfile)); 
     errStream.println("file open, ready to send"); 
     errorcount = 0; 
     blocknumber = 1; 

     // The C version uses "alarm()", a UNIX-only system call, 
     // to detect if the read times out. Here we do detect it 
     // by using a Thread, the IOTimer class defined above. 
     gotChar = false; 
     new IOTimer(SENTIMOUT, "NAK to start send").start(); 

     do { 
      character = getchar(); 
      gotChar = true; 
      if (character != NAK && errorcount < MAXERRORS) 
       ++errorcount; 
     } while (character != NAK && errorcount < MAXERRORS); 

     errStream.println("transmission beginning"); 
     if (errorcount == MAXERRORS) { 
      xerror(); 
     } 

     while ((nbytes=inStream.read(sector))!=0) { 
      if (nbytes<SECSIZE) 
       sector[nbytes]=CPMEOF; 
      errorcount = 0; 
      while (errorcount < MAXERRORS) { 
       errStream.println("{" + blocknumber + "} "); 
       putchar(SOH); /* here is our header */ 
       putchar(blocknumber); /* the block number */ 
       putchar(~blocknumber); /* & its complement */ 
       checksum = 0; 
       for (index = 0; index < SECSIZE; index++) { 
        putchar(sector[index]); 
        checksum += sector[index]; 
       } 
       putchar(checksum); /* tell our checksum */ 
       if (getchar() != ACK) 
        ++errorcount; 
       else 
        break; 
      } 
      if (errorcount == MAXERRORS) 
       xerror(); 
      ++blocknumber; 
     } 
     boolean isAck = false; 
     while (!isAck) { 
      putchar(EOT); 
      isAck = getchar() == ACK; 
     } 
     errStream.println("Transmission complete."); 
     return true; 
    } 

    /* 
    * receive a file from the remote 
    */ 
    public boolean receive(String tfile) throws IOException, InterruptedException 
    { 
     char checksum, index, blocknumber, errorcount; 
     byte character; 
     byte[] sector = new byte[SECSIZE]; 
     DataOutputStream foo; 

     foo = new DataOutputStream(new FileOutputStream(tfile)); 

     System.out.println("you have " + SLEEP + " seconds..."); 

     /* wait for the user or remote to get his act together */ 
     gotChar = false; 
     new IOTimer(SLEEP, "receive from remote").start(); 

     errStream.println("Starting receive..."); 
     putchar(NAK); 
     errorcount = 0; 
     blocknumber = 1; 
     rxLoop: 
     do { 
      character = getchar(); 
      gotChar = true; 
      if (character != EOT) { 
       try { 
        byte not_ch; 
        if (character != SOH) { 
         errStream.println("Not SOH"); 
         if (++errorcount < MAXERRORS) 
          continue rxLoop; 
         else 
          xerror(); 
        } 
        character = getchar(); 
        not_ch = (byte)(~getchar()); 
        errStream.println("[" + character + "] "); 
        if (character != not_ch) { 
         errStream.println("Blockcounts not ~"); 
         ++errorcount; 
         continue rxLoop; 
        } 
        if (character != blocknumber) { 
         errStream.println("Wrong blocknumber"); 
         ++errorcount; 
         continue rxLoop; 
        } 
        checksum = 0; 
        for (index = 0; index < SECSIZE; index++) { 
         sector[index] = getchar(); 
         checksum += sector[index]; 
        } 
        if (checksum != getchar()) { 
         errStream.println("Bad checksum"); 
         errorcount++; 
         continue rxLoop; 
        } 
        putchar(ACK); 
        blocknumber++; 
        try { 
         foo.write(sector); 
        } catch (IOException e) { 
         errStream.println("write failed, blocknumber " + blocknumber); 
        } 
       } finally { 
       if (errorcount != 0) 
        putchar(NAK); 
      } 
     } 
     } while (character != EOT); 

     foo.close(); 

     putchar(ACK); /* tell the other end we accepted his EOT */ 
     putchar(ACK); 
     putchar(ACK); 

     errStream.println("Receive Completed."); 
     return true; 
    } 

    protected byte getchar() throws IOException { 
     return (byte)inStream.read(); 
    } 

    protected void putchar(int c) throws IOException { 
     outStream.write(c); 
    } 

    protected void xerror() 
    { 
     errStream.println("too many errors...aborting"); 
     die(1); 
    } 

    protected void die(int how) 
    { 
     if (standalone) 
      System.exit(how); 
     else 
      System.out.println(("Error code " + how)); 
    } 
} 
+0

@sumesh가 당신을 위해이 운동을 했습니까? –

0

이 프로그램이 실제로 작동합니까? 나는 그것을 사용하려고 노력하고있다. 그러나 나는 항상 예외를 얻는다. send 부분에서 코드는 파일 이름을 전혀 사용하지 않습니다 ...

JModem을 사용하는 경우 전송 버튼을 클릭하면 다른 쪽 끝은 문자열 "tmodem -r at.ht"또는 - 당신이받는다면. 하지만이 문자열이 아무것도하지 않고 끝나는 것을 보지 못했습니다 ... 텍스트 영역에만 표시됩니다 ...