////////////////////////////////////////////////////////////////////////////
// by Michael Kroll 22.August 2000
// 2001-03-11 fixed a bug in openOutputStream and openInputStream 
// 2001-03-16 fixed a bug in import !
////////////////////////////////////////////////////////////////////////////

package com.sun.cldc.io.j2se.comm;

import java.io.*;
import java.net.*;
import java.util.*;
import javax.microedition.io.*;
import com.sun.cldc.io.j2se.*;
import com.sun.cldc.io.*;

import javax.comm.*;

public class Protocol extends ConnectionBase implements StreamConnection {
    
    int opens = 0;
    
    Enumeration portList;
    CommPortIdentifier portId;
    SerialPort serialPort;

    String comport = "COM1";
    int baudrate = 9600;
    int databits = SerialPort.DATABITS_8;
    int stopbits = SerialPort.STOPBITS_1;
    int parity = SerialPort.PARITY_NONE;


    public void open (String name, int mode, boolean timeouts) throws IOException {
        throw new RuntimeException ("Should not be called");
    }


    public Connection openPrim (String name, int mode, boolean timeouts) throws IOException {
	
	if (name.charAt (0) == '0') {
	    comport = "COM1";
	} else if (name.charAt (0) == '1') {
	    comport = "COM2";
	} else if (name.charAt (0) == '2') {
	    comport = "COM3";
	} else if (name.charAt (0) == '3'){
	    comport = "COM4";
	} else {
	    throw new IllegalArgumentException ("Protocol must start with \"0\" or \"1\" or \"2\" or \"3\" "+name);
	}
	

	Hashtable ht = new Hashtable ();
	
	StringTokenizer st = new StringTokenizer (name, ";");
	while (st.hasMoreTokens()) {
	    String param = st.nextToken ();
	    
	    int idx = param.indexOf ("=");
	    if (idx == -1) {
		ht.put ("commport", param);
	    } else {
		ht.put (param.substring (0, idx), param.substring (idx+1, param.length ())); 
	    }
	}
	
	// Parameter auswerten

	if (ht.containsKey ("commport")) {
	    int port = 0;
	    try {
		port = Integer.parseInt ((String)ht.get ("commport"));
	    } catch (NumberFormatException e) {
		throw new IllegalArgumentException ("Specified comport not supported " + name);
	    }
	    switch (port) {
	    case 0: comport = "COM1";
		break;
	    case 1: comport = "COM2";
		    break;
	    case 2: comport = "COM3";
		break;
	    case 3: comport = "COM4";
	    } 
	}

	if (ht.containsKey ("baudrate")) {
	    String baud = (String)ht.get ("baudrate");
	    
	    if (baud.equals ("57600")) {
		baudrate = 57600;
	    } else if (baud.equals ("38400")) {
		baudrate = 38400;
	    } else if (baud.equals ("19200")) {
		baudrate = 19200;
	    } else if (baud.equals ("9600")) {
		baudrate = 9600;
	    } else if (baud.equals ("2400")) {
		baudrate = 2400;
	    } else if (baud.equals ("1200")) {
		baudrate = 1200;
	    } else if (baud.equals ("300")) {
		baudrate = 300;
	    } else 
		throw new IllegalArgumentException ("Specified baudrate not supported " + name);
	}
	
	if (ht.containsKey ("bitsperchar")) {
	    String bits = (String)ht.get ("bitsperchar");
	    if (bits.equals ("8")) {
		databits = SerialPort.DATABITS_8;
	    } else if (bits.equals ("7")) {
		databits = SerialPort.DATABITS_7;
	    } else 
		throw new IllegalArgumentException ("Specified bitnumber not supported " + name);
	}
	
	if (ht.containsKey ("parity")) {
	    String pari = (String)ht.get ("parity");
	    if (pari.equals ("none")) {
		parity = SerialPort.PARITY_NONE;;
	    } else if (pari.equals ("odd")) {
		parity = SerialPort.PARITY_ODD;
	    } else if (pari.equals ("even")) {
		parity = SerialPort.PARITY_EVEN;
	    } else 
		throw new IllegalArgumentException ("Specified parity not supported " + name);
	}
	
	portList = CommPortIdentifier.getPortIdentifiers();
	
        while (portList.hasMoreElements()) {
            portId = (CommPortIdentifier) portList.nextElement();
            if (portId.getPortType() == CommPortIdentifier.PORT_SERIAL) {
		if (portId.getName().equals(comport)) {
		    
		    try {
                        serialPort = (SerialPort) portId.open("com.sun.cldc.j2se.comm", 2000);
                    } catch (PortInUseException e) {
			System.out.println (e);
		    }
                    
		    try {
                        serialPort.setSerialPortParams(baudrate, databits, stopbits, parity);
                    } catch (UnsupportedCommOperationException e) {
			System.out.println (e);
		    }
		}
            }
        }
	return this;
    }
    
    
    public InputStream openInputStream () throws IOException {
	UniversalFilterInputStream is = new UniversalFilterInputStream (this, serialPort.getInputStream());
        opens++;
        return is;
    }
    
    
    public OutputStream openOutputStream () throws IOException {
        UniversalFilterOutputStream os = new UniversalFilterOutputStream (this, serialPort.getOutputStream());
        opens++;
        return os;
    }
    
    
    public void close() throws IOException {
        if(--opens == 0) {
	    serialPort.close();
	}
    }
}


