63 char *ec_master_version_str = EC_MASTER_VERSION; /**< Version string. */ |
63 char *ec_master_version_str = EC_MASTER_VERSION; /**< Version string. */ |
64 unsigned int debug_level = 0; |
64 unsigned int debug_level = 0; |
65 |
65 |
66 static struct tty_driver *tty_driver = NULL; |
66 static struct tty_driver *tty_driver = NULL; |
67 ec_tty_t *ttys[EC_TTY_MAX_DEVICES]; |
67 ec_tty_t *ttys[EC_TTY_MAX_DEVICES]; |
68 struct semaphore tty_sem; |
68 struct ec_mutex_t tty_sem; |
69 |
69 |
70 void ec_tty_wakeup(unsigned long); |
70 void ec_tty_wakeup(unsigned long); |
71 |
71 |
72 /*****************************************************************************/ |
72 /*****************************************************************************/ |
73 |
73 |
109 unsigned int rx_write_idx; |
109 unsigned int rx_write_idx; |
110 |
110 |
111 struct timer_list timer; |
111 struct timer_list timer; |
112 struct tty_struct *tty; |
112 struct tty_struct *tty; |
113 unsigned int open_count; |
113 unsigned int open_count; |
114 struct semaphore sem; |
114 struct ec_mutex_t sem; |
115 |
115 |
116 ec_tty_operations_t ops; |
116 ec_tty_operations_t ops; |
117 void *cb_data; |
117 void *cb_data; |
118 }; |
118 }; |
119 |
119 |
200 t->rx_read_idx = 0; |
200 t->rx_read_idx = 0; |
201 t->rx_write_idx = 0; |
201 t->rx_write_idx = 0; |
202 init_timer(&t->timer); |
202 init_timer(&t->timer); |
203 t->tty = NULL; |
203 t->tty = NULL; |
204 t->open_count = 0; |
204 t->open_count = 0; |
205 sema_init(&t->sem, 1); |
205 ec_mutex_init(&t->sem); |
206 t->ops = *ops; |
206 t->ops = *ops; |
207 t->cb_data = cb_data; |
207 t->cb_data = cb_data; |
208 |
208 |
209 t->dev = tty_register_device(tty_driver, t->minor, NULL); |
209 t->dev = tty_register_device(tty_driver, t->minor, NULL); |
210 if (IS_ERR(t->dev)) { |
210 if (IS_ERR(t->dev)) { |
407 printk(KERN_INFO PFX "%s(tty=%p, file=%p): Closing line %i.\n", |
407 printk(KERN_INFO PFX "%s(tty=%p, file=%p): Closing line %i.\n", |
408 __func__, tty, file, tty->index); |
408 __func__, tty, file, tty->index); |
409 #endif |
409 #endif |
410 |
410 |
411 if (t) { |
411 if (t) { |
412 down(&t->sem); |
412 ec_mutex_lock(&t->sem); |
413 if (--t->open_count == 0) { |
413 if (--t->open_count == 0) { |
414 t->tty = NULL; |
414 t->tty = NULL; |
415 } |
415 } |
416 up(&t->sem); |
416 ec_mutex_unlock(&t->sem); |
417 } |
417 } |
418 } |
418 } |
419 |
419 |
420 /*****************************************************************************/ |
420 /*****************************************************************************/ |
421 |
421 |
674 ec_tty_t *ectty_create(const ec_tty_operations_t *ops, void *cb_data) |
674 ec_tty_t *ectty_create(const ec_tty_operations_t *ops, void *cb_data) |
675 { |
675 { |
676 ec_tty_t *tty; |
676 ec_tty_t *tty; |
677 int minor, ret; |
677 int minor, ret; |
678 |
678 |
679 if (down_interruptible(&tty_sem)) { |
679 if (ec_mutex_lock_interruptible(&tty_sem)) { |
680 return ERR_PTR(-EINTR); |
680 return ERR_PTR(-EINTR); |
681 } |
681 } |
682 |
682 |
683 for (minor = 0; minor < EC_TTY_MAX_DEVICES; minor++) { |
683 for (minor = 0; minor < EC_TTY_MAX_DEVICES; minor++) { |
684 if (!ttys[minor]) { |
684 if (!ttys[minor]) { |
685 printk(KERN_INFO PFX "Creating TTY interface %i.\n", minor); |
685 printk(KERN_INFO PFX "Creating TTY interface %i.\n", minor); |
686 |
686 |
687 tty = kmalloc(sizeof(ec_tty_t), GFP_KERNEL); |
687 tty = kmalloc(sizeof(ec_tty_t), GFP_KERNEL); |
688 if (!tty) { |
688 if (!tty) { |
689 up(&tty_sem); |
689 ec_mutex_unlock(&tty_sem); |
690 printk(KERN_ERR PFX "Failed to allocate memory.\n"); |
690 printk(KERN_ERR PFX "Failed to allocate memory.\n"); |
691 return ERR_PTR(-ENOMEM); |
691 return ERR_PTR(-ENOMEM); |
692 } |
692 } |
693 |
693 |
694 ret = ec_tty_init(tty, minor, ops, cb_data); |
694 ret = ec_tty_init(tty, minor, ops, cb_data); |
695 if (ret) { |
695 if (ret) { |
696 up(&tty_sem); |
696 ec_mutex_unlock(&tty_sem); |
697 kfree(tty); |
697 kfree(tty); |
698 return ERR_PTR(ret); |
698 return ERR_PTR(ret); |
699 } |
699 } |
700 |
700 |
701 ttys[minor] = tty; |
701 ttys[minor] = tty; |
702 up(&tty_sem); |
702 ec_mutex_unlock(&tty_sem); |
703 return tty; |
703 return tty; |
704 } |
704 } |
705 } |
705 } |
706 |
706 |
707 up(&tty_sem); |
707 ec_mutex_unlock(&tty_sem); |
708 printk(KERN_ERR PFX "No free interfaces avaliable.\n"); |
708 printk(KERN_ERR PFX "No free interfaces avaliable.\n"); |
709 return ERR_PTR(-EBUSY); |
709 return ERR_PTR(-EBUSY); |
710 } |
710 } |
711 |
711 |
712 /*****************************************************************************/ |
712 /*****************************************************************************/ |