⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ark3116.c

📁 采用ark 3116芯片组的usb转rs232接口线的linux下驱动程序
💻 C
📖 第 1 页 / 共 2 页
字号:
	ARK3116_SND( 119,0xFE,0x40,0x0000,0x0004);	ARK3116_RCV( 120,0xFE,0xC0,0x0000,0x0004, 0x00); //returns 0	ARK3116_SND( 121,0xFE,0x40,0x0001,0x0004);	ARK3116_RCV( 122,0xFE,0xC0,0x0000,0x0004, 0x01); //returns 1		ARK3116_SND( 123,0xFE,0x40,0x0003,0x0004);		ARK3116_RCV( 124,0xFE,0xC0,0x0000,0x0006, 0xFF); //returns different values (control lines ?!)		//initialise termios:	if (port->tty) {		ark3116_set_termios (port, &tmp_termios);	}	kfree(buf);	//ok	return(result);}	static void ark3116_set_termios (struct usb_serial_port *port, struct termios *old_termios){	/* ark3116_set_termios */	struct usb_serial *serial = port->serial;        struct ark3116_private *priv = usb_get_serial_port_data(port);	unsigned int cflag = port->tty->termios->c_cflag;	unsigned long flags;	int baud;	int ark3116_baud;	char *buf;	char config;	int rst;		rst=0;	config=0;		//dbg ("ark3116_set_termios port %d", port->number);	dbg("%s - port %d", __FUNCTION__, port->number);	if ((!port->tty) || (!port->tty->termios)) {		dbg("%s - no tty structures", __FUNCTION__);		return;	}	spin_lock_irqsave(&priv->lock, flags);	if (!priv->termios_initialized) {		*(port->tty->termios) = tty_std_termios;		port->tty->termios->c_cflag = B9600 | CS8 | CREAD | HUPCL | CLOCAL;		priv->termios_initialized = 1;	}	spin_unlock_irqrestore(&priv->lock, flags);		cflag = port->tty->termios->c_cflag;		//check that they really want us to change something:	if (old_termios) {		if ((cflag == old_termios->c_cflag)){			//&& (RELEVANT_IFLAG(port->tty->termios->c_iflag) == RELEVANT_IFLAG(old_termios->c_iflag))) {			dbg("%s - nothing to change...", __FUNCTION__);			return;		}	}	buf = kmalloc(1, GFP_KERNEL);	if (!buf) {		dbg("error kmalloc");		return;	}	//set data bit count (8/7/6/5)	if (cflag & CSIZE){		switch (cflag & CSIZE){			case CS5: config |= 0x00; dbg ("setting CS5"); break;			case CS6: config |= 0x01; dbg ("setting CS6"); break;			case CS7: config |= 0x02; dbg ("setting CS7"); break;			default:  err ("CSIZE was set but not CS5-CS8, using CS8!");			case CS8: config |= 0x03; dbg ("setting CS8"); break;		}	}	//set parity (NONE,EVEN,ODD)	if (cflag & PARENB){		if (cflag & PARODD){			config |= 0x08;			dbg ("setting parity to ODD");		}else{			config |= 0x18;			dbg ("setting parity to EVEN");		}	}else{		dbg ("setting parity to NONE");	}	//SET STOPBIT (1/2)	if (cflag & CSTOPB){		config |= 0x04;		dbg ("setting 2 stop bits");	}else{		dbg ("setting 1 stop bit");	}		//set baudrate:	baud = 0;	switch (cflag & CBAUD){		case B0:        err ("can't set 0baud, using 9600 instead");  break;		case B75:       baud = 75;      break;		case B150:      baud = 150;     break;		case B300:      baud = 300;     break;		case B600:      baud = 600;     break;		case B1200:     baud = 1200;    break;		case B1800:     baud = 1800;    break;		case B2400:     baud = 2400;    break;		case B4800:     baud = 4800;    break;		case B9600:     baud = 9600;    break;		case B19200:    baud = 19200;   break;		case B38400:    baud = 38400;   break;		case B57600:    baud = 57600;   break;		case B115200:   baud = 115200;  break;		case B230400:   baud = 230400;  break;		case B460800:   baud = 460800;  break;		default:	dbg ("ark3116 driver does not support the baudrate requested (fix it)"); break;	}		//set 9600 as default (if given baudrate is invalid for example)	if (baud==0)		baud = 9600;	//found by try'n'error, be careful, maybe there are other options for multiplicator etc!	if (baud == 460800)		ark3116_baud = 7; //strange, for 460800 the formula is wrong (dont use round(), then 9600baud is wrong)	else		ark3116_baud = 3000000 / baud;	//?	ARK3116_RCV(000,0xFE,0xC0,0x0000,0x0003, 0x03);	//offset = buf[0];	//offset = 0x03;	//dbg("using 0x%04X as target for 0x0003:",0x0080+offset);			//set baudrate	dbg ("setting baudrate to %d (->reg=%d)",baud,ark3116_baud);	ARK3116_SND(147,0xFE,0x40,0x0083,0x0003);	ARK3116_SND(148,0xFE,0x40,(ark3116_baud & 0x00FF)   ,0x0000);	ARK3116_SND(149,0xFE,0x40,(ark3116_baud & 0xFF00)>>8,0x0001);	ARK3116_SND(150,0xFE,0x40,0x0003,0x0003);	//?	ARK3116_RCV(151,0xFE,0xC0,0x0000,0x0004,0x03);	ARK3116_SND(152,0xFE,0x40,0x0000,0x0003);	//set data bit count, stop bit count & parity:	dbg ("updating bit count, stop bit or parity (cfg=0x%02X)", config);	ARK3116_RCV(153,0xFE,0xC0,0x0000,0x0003,0x00);	ARK3116_SND(154,0xFE,0x40,config,0x0003);		if (cflag & CRTSCTS){		dbg ("CRTSCTS not supported by chipset ?!");	}	//TEST//ARK3116_SND(154,0xFE,0x40,0xFFFF, 0x0006);		kfree(buf);	return;}//stolen from generic.cstatic void ark3116_read_bulk_callback (struct urb *urb, struct pt_regs *regs){        struct usb_serial_port *port = (struct usb_serial_port *)urb->context;        struct usb_serial *serial = port->serial;        struct tty_struct *tty;        unsigned char *data = urb->transfer_buffer;        int result;        dbg("%s - port %d", __FUNCTION__, port->number);        if (urb->status) {                dbg("%s - nonzero read bulk status received: %d", __FUNCTION__, urb->status);                return;        }        usb_serial_debug_data(debug, &port->dev, __FUNCTION__, urb->actual_length, data);        tty = port->tty;        if (tty && urb->actual_length) {                tty_buffer_request_room(tty, urb->actual_length);		tty_insert_flip_string(tty, data, urb->actual_length);		tty_flip_buffer_push(tty);        }        /* Continue trying to always read  */        usb_fill_bulk_urb (port->read_urb, serial->dev,                           usb_rcvbulkpipe (serial->dev,                                            port->bulk_in_endpointAddress),                           port->read_urb->transfer_buffer,                           port->read_urb->transfer_buffer_length,                           ((serial->type->read_bulk_callback) ?                             serial->type->read_bulk_callback :                             ark3116_read_bulk_callback), port);        result = usb_submit_urb(port->read_urb, GFP_ATOMIC);        if (result)                dev_err(&port->dev, "%s - failed resubmitting read urb, error %d\n", __FUNCTION__, result);}static int ark3116_ioctl (struct usb_serial_port *port, struct file *file, unsigned int cmd, unsigned long arg){	dbg ("ioctl not supported yet...");	return -ENOIOCTLCMD;}static int ark3116_tiocmget (struct usb_serial_port *port, struct file *file){	struct usb_serial *serial = port->serial;	char buf[1];	int rst;			     	//seems like serial port status info (RTS, CTS,...) is stored in reg(?) 0x0006	//pcb connection point 11 = GND -> sets bit4 of response        //pcb connection point  7 = GND -> sets bit6 of response	//read register:	ARK3116_RCV_QUIET(0xFE,0xC0,0x0000,0x0006);	//i do not really know if bit4=CTS and bit6=DSR... was just a quick guess !!	return  (buf[0] & (1<<4) ? TIOCM_CTS : 0) |		(buf[0] & (1<<6) ? TIOCM_DSR : 0);}static int __init ark3116_init(void){	int retval;	retval = usb_serial_register(&ark3116_device);	if (retval)		return retval;	retval = usb_register(&ark3116_driver);	if (retval)		usb_serial_deregister(&ark3116_device);	return retval;}static void __exit ark3116_exit(void){	usb_deregister(&ark3116_driver);	usb_serial_deregister(&ark3116_device);}module_param(debug, bool, S_IRUGO | S_IWUSR);MODULE_PARM_DESC(debug, "Debug enabled or not");module_init(ark3116_init);module_exit(ark3116_exit);MODULE_LICENSE("GPL");

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -