00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00029 #ifdef HAVE_CONFIG_H
00030 #include "config/config.h"
00031 #endif
00032 #include <linux/module.h>
00033 #include <linux/fs.h>
00034 #include <linux/dma-mapping.h>
00035 #include <linux/timer.h>
00036 #include <linux/rwsem.h>
00037 #include <asm/msr.h>
00038 #include <asm/system.h>
00039 #include <asm/semaphore.h>
00040 #include <asm/uaccess.h>
00041
00042 #include "most-constants.h"
00043 #include "most-base.h"
00044 #include "most-sync-rt.h"
00045 #include "most-common-rt.h"
00046 #include "most-rxbuf.h"
00047 #include "most-txbuf.h"
00048 #include "serial-rt-debug.h"
00049 #include "most-measurements.h"
00050
00054 #define DRIVER_NAME "most-sync-rt"
00055
00059 #define DRIVER_MAJOR_VERSION 0
00060
00064 #define DRIVER_MINOR_VERSION 1
00065
00069 #define DRIVER_PATHLEVEL 0
00070
00074 #define PR DRIVER_NAME ": "
00075
00076
00077 #include "most-sync-common.h"
00078
00082 static char *version = "$Rev: 170 $";
00083
00087 struct most_sync_rt_dev *most_sync_rt_devices[MOST_DEVICE_NUMBER];
00088
00089
00090 static int most_sync_nrt_open (struct rtdm_dev_context *, rtdm_user_info_t *, int);
00091 static int most_sync_nrt_close (struct rtdm_dev_context *, rtdm_user_info_t *);
00092 static int most_sync_nrt_ioctl (struct rtdm_dev_context *, rtdm_user_info_t *,
00093 int, void *);
00094 static ssize_t most_sync_rt_read (struct rtdm_dev_context *, rtdm_user_info_t *,
00095 void *, size_t);
00096 static ssize_t most_sync_rt_write (struct rtdm_dev_context *, rtdm_user_info_t *,
00097 const void *, size_t);
00098
00099
00100
00101
00102
00103
00104 long sw_rx_buffer_size = STD_MOST_FRAMES_PER_SEC;
00105
00106
00107
00108
00109 long sw_tx_buffer_size = STD_MOST_FRAMES_PER_SEC;
00110
00111
00112
00113
00114 long hw_rx_buffer_size = 44;
00115
00116
00117
00118
00119 long hw_tx_buffer_size = 44;
00120
00124 #ifdef SYNC_DEBUG
00125 static serial_rt_t s_serial_fd;
00126 #endif
00127
00128 #ifndef DOXYGEN
00129 module_param(sw_rx_buffer_size, long, S_IRUGO);
00130 MODULE_PARM_DESC(sw_rx_buffer_size,
00131 "Size of the software receive buffer in frame parts "
00132 "(default: " __MODULE_STRING(STD_MOST_FRAMES_PER_SEC) ")");
00133
00134 module_param(sw_tx_buffer_size, long, S_IRUGO);
00135 MODULE_PARM_DESC(sw_tx_buffer_size,
00136 "Size of the software transmit buffer in frame parts "
00137 "(default: " __MODULE_STRING(STD_MOST_FRAMES_PER_SEC) ")");
00138
00139 module_param(hw_rx_buffer_size, long, S_IRUGO);
00140 MODULE_PARM_DESC(hw_rx_buffer_size,
00141 "Size of the hardware receive buffer in frame parts "
00142 "(default: " __MODULE_STRING(44) ")");
00143
00144 module_param(hw_tx_buffer_size, long, S_IRUGO);
00145 MODULE_PARM_DESC(hw_tx_buffer_size,
00146 "Size of the hardware transmit buffer in frame parts "
00147 "(default: " __MODULE_STRING(44) ")");
00148 #endif
00149
00150
00151
00156 static const struct rtdm_device device_templ = {
00157 .struct_version = RTDM_DEVICE_STRUCT_VER,
00158
00159 .device_flags = RTDM_NAMED_DEVICE,
00160 .context_size = sizeof(struct most_sync_rt_file),
00161 .device_name = "",
00162
00163 .open_rt = NULL,
00164 .open_nrt = most_sync_nrt_open,
00165
00166 .ops = {
00167 .close_rt = NULL,
00168 .close_nrt = most_sync_nrt_close,
00169
00170 .ioctl_rt = NULL,
00171 .ioctl_nrt = most_sync_nrt_ioctl,
00172
00173 .read_rt = most_sync_rt_read,
00174 .read_nrt = NULL,
00175
00176 .write_rt = most_sync_rt_write,
00177 .write_nrt = NULL,
00178 },
00179
00180 .device_class = RTDM_CLASS_MOSTSYNC,
00181 .device_sub_class = RTDM_SUBCLASS_MOSTSYNC_OASIS,
00182 .driver_name = DRIVER_NAME,
00183 .driver_version = RTDM_DRIVER_VER(DRIVER_MAJOR_VERSION,
00184 DRIVER_MINOR_VERSION,
00185 DRIVER_PATHLEVEL),
00186 .peripheral_name = "MOST Synchronous Access for PCI Interface",
00187 .provider_name = "Bernhard Walle",
00188 };
00189
00196 static inline void most_sync_nrt_stop_rx(struct most_sync_rt_file *file)
00197 {
00198 most_sync_stop_rx_common(file->sync_dev, file);
00199 }
00200
00207 static inline void most_sync_nrt_stop_tx(struct most_sync_rt_file *file)
00208 {
00209 most_sync_stop_tx_common(file->sync_dev, file);
00210 }
00211
00223 static inline int most_sync_nrt_reconfigure_begin(struct most_conf_sync *sync)
00224 {
00225 int err;
00226 bool ok_to_continue = false;
00227
00228 while (true) {
00229 RTDM_EXECUTE_ATOMICALLY(
00230 ok_to_continue = !sync->reconfigure_flag && sync->counter == 0;
00231 if (ok_to_continue)
00232 sync->reconfigure_flag = true;
00233 );
00234
00235 if (ok_to_continue) {
00236 break;
00237 }
00238
00239
00240 err = wait_event_interruptible(sync->wait_reconfigure,
00241 !sync->reconfigure_flag && sync->counter == 0);
00242 if (err < 0) {
00243 return err;
00244 }
00245 }
00246
00247 return 0;
00248 }
00249
00258 static inline void most_sync_nrt_reconfigure_end(struct most_conf_sync *sync)
00259 {
00260 RTDM_EXECUTE_ATOMICALLY(
00261 sync->reconfigure_flag = false;
00262
00263
00264 rtdm_event_pulse(&sync->wait_read_write);
00265
00266
00267 wake_up_interruptible(&sync->wait_reconfigure);
00268 );
00269 }
00270
00285 static inline int most_sync_rt_read_write_begin(struct most_conf_sync *sync)
00286 {
00287 int err = 0;
00288
00289 return_value_if_fails_dbg(sync != NULL, -EINVAL);
00290 assert(sync->counter >= 0);
00291
00292
00293 RTDM_EXECUTE_ATOMICALLY(
00294 if (sync->reconfigure_flag)
00295 err = rtdm_event_wait(&sync->wait_read_write);
00296
00297
00298
00299
00300
00301 if (err >= 0)
00302 sync->counter++;
00303 );
00304
00305 return err;
00306 }
00307
00316 static inline void most_sync_rt_read_write_end(struct most_conf_sync *sync)
00317 {
00318
00319
00320
00321
00322 RTDM_EXECUTE_ATOMICALLY(
00323
00324 if (--sync->counter == 0)
00325 wake_up_interruptible(&sync->wait_reconfigure);
00326 );
00327
00328 assert(sync->counter >= 0);
00329 }
00330
00345 static int most_sync_nrt_open(struct rtdm_dev_context *context,
00346 rtdm_user_info_t *user_info,
00347 int oflag)
00348 {
00349 struct most_sync_rt_dev *sync_dev;
00350 struct most_sync_rt_file *file = (void *)context->dev_private;
00351
00352 sync_dev = container_of((struct rtdm_device *)context->device,
00353 struct most_sync_rt_dev, rtdm_dev);
00354 most_manage_usage(sync_dev->most_dev, 1);
00355
00356 pr_sync_debug(PR "most_sync_open called for PCI card %d\n",
00357 MOST_DEV_CARDNUMBER(sync_dev->most_dev));
00358
00359
00360 memset(file, 0, sizeof(struct most_sync_rt_file));
00361 INIT_LIST_HEAD(&file->list);
00362 file->sync_dev = sync_dev;
00363
00364
00365 if (atomic_inc_and_test(&sync_dev->open_count)) {
00366 rtnrt_err(PR "Too much open (%d) for a MOST device,"
00367 " only %d allowed\n", atomic_read(&sync_dev->open_count),
00368 MOST_SYNC_OPENS);
00369 goto out_dec;
00370 }
00371
00372
00373 rtdm_lock_get(&sync_dev->lock);
00374 list_add_tail(&file->list, &sync_dev->file_list);
00375 rtdm_lock_put(&sync_dev->lock);
00376
00377 return 0;
00378
00379 out_dec:
00380 atomic_dec(&sync_dev->open_count);
00381 most_manage_usage(sync_dev->most_dev, -1);
00382 return -EBUSY;
00383 }
00384
00393 static int most_sync_nrt_close(struct rtdm_dev_context *context,
00394 rtdm_user_info_t *user_info)
00395 {
00396 struct most_sync_rt_file *file = (void *)context->dev_private;
00397 struct most_sync_rt_dev *sync_dev = file->sync_dev;
00398 int err = 0, count = 0;
00399
00400 pr_sync_debug(PR "most_sync_rt_close called for PCI card %d\n",
00401 MOST_DEV_CARDNUMBER(sync_dev->most_dev));;
00402
00403
00404 rtdm_lock_get(&sync_dev->lock);
00405 list_del(&file->list);
00406 rtdm_lock_put(&sync_dev->lock);
00407
00408
00409 do {
00410 if (file->rx_running && atomic_dec_and_test(&sync_dev->receiver_count)) {
00411 pr_sync_debug(PR "Last Reader\n");
00412 err = most_sync_nrt_reconfigure_begin(&sync_dev->rx_sync);
00413 if (err >= 0) {
00414 most_sync_last_closed_rx(sync_dev, file, most_sync_nrt_stop_rx);
00415 most_sync_nrt_reconfigure_end(&sync_dev->rx_sync);
00416 }
00417 }
00418
00419
00420 if (file->tx_running && atomic_dec_and_test(&sync_dev->transmitter_count)) {
00421 pr_sync_debug(PR "Last Transmitter\n");
00422 err = most_sync_nrt_reconfigure_begin(&sync_dev->tx_sync);
00423 if (err >= 0) {
00424 most_sync_last_closed_tx(sync_dev, file, most_sync_nrt_stop_tx);
00425 most_sync_nrt_reconfigure_end(&sync_dev->tx_sync);
00426 }
00427 }
00428 } while (err != 0 && count++ < MAX_RETRIES);
00429
00430 if (count != 0) {
00431 rtnrt_warn(PR "Aquiring the lock failed %d times, err = %d\n", count, err);
00432 }
00433
00434 most_manage_usage(sync_dev->most_dev, -1);
00435 atomic_dec(&sync_dev->open_count);
00436
00437 return 0;
00438 }
00439
00448 static inline int most_sync_nrt_setup_rx(struct most_sync_rt_file *file,
00449 rtdm_user_info_t *user_info,
00450 void *ioctl_arg)
00451 {
00452 struct frame_part *arg = (struct frame_part *)ioctl_arg;
00453 struct most_sync_rt_dev *sync_dev = file->sync_dev;
00454 int err = 0;
00455 struct frame_part param;
00456
00457
00458 copy_from_user_or_kernel(err, user_info, ¶m, arg, sizeof(struct frame_part));
00459 if (unlikely(err != 0)) {
00460 return -EFAULT;
00461 }
00462
00463 pr_sync_debug(PR "size = %d, offset = %d\n", param.count,
00464 param.offset);
00465
00466
00467 err = most_sync_nrt_reconfigure_begin(&sync_dev->rx_sync);
00468 if (err < 0) {
00469 return err;
00470 }
00471
00472
00473 if (file->rx_running) {
00474 most_sync_nrt_stop_rx(file);
00475 }
00476
00477 most_sync_setup_rx_common(param, file, sync_dev, hw_rx_buffer_size,
00478 sw_rx_buffer_size, err, most_sync_rt_file);
00479
00480 most_sync_nrt_reconfigure_end(&sync_dev->rx_sync);
00481
00482 return err;
00483 }
00484
00493 static inline int most_sync_nrt_setup_tx(struct most_sync_rt_file *file,
00494 rtdm_user_info_t *user_info,
00495 void *ioctl_arg)
00496 {
00497 struct frame_part *arg = (struct frame_part *)ioctl_arg;
00498 struct most_sync_rt_dev *sync_dev = file->sync_dev;
00499 int err = 0;
00500 struct frame_part param;
00501
00502
00503 copy_from_user_or_kernel(err, user_info, ¶m, arg, sizeof(struct frame_part));
00504 if (unlikely(err != 0)) {
00505 return -EFAULT;
00506 }
00507
00508
00509 err = most_sync_nrt_reconfigure_begin(&sync_dev->tx_sync);
00510 if (err < 0) {
00511 return err;
00512 }
00513
00514
00515 if (file->tx_running) {
00516 most_sync_nrt_stop_rx(file);
00517 }
00518
00519 most_sync_setup_tx_common(param, file, sync_dev, hw_tx_buffer_size,
00520 sw_tx_buffer_size, err, most_sync_rt_file);
00521 most_sync_nrt_reconfigure_end(&sync_dev->tx_sync);
00522
00523 return err;
00524 }
00525
00536 static int most_sync_nrt_ioctl(struct rtdm_dev_context *context,
00537 rtdm_user_info_t *user_info,
00538 int request,
00539 void *arg)
00540 {
00541 struct most_sync_rt_file *file = (void *)context->dev_private;
00542 int err = 0;
00543
00544
00545
00546
00547
00548 if (unlikely((_IOC_TYPE(request) != MOST_SYNC_RT_IOCTL_MAGIC))) {
00549 return -ENOTTY;
00550 }
00551
00552
00553 if (user_info) {
00554 if (_IOC_DIR(request) & _IOC_READ) {
00555 err = !rtdm_read_user_ok(user_info, arg, _IOC_SIZE(request));
00556 } else if (_IOC_DIR(request) & _IOC_WRITE) {
00557 err = !rtdm_rw_user_ok(user_info, arg, _IOC_SIZE(request));
00558 }
00559
00560 if (err) {
00561 return -EFAULT;
00562 }
00563 }
00564
00565
00566 switch (request) {
00567 case MOST_SYNC_RT_SETUP_RX:
00568 return most_sync_nrt_setup_rx(file, user_info, arg);
00569
00570 case MOST_SYNC_RT_SETUP_TX:
00571 return most_sync_nrt_setup_tx(file, user_info, arg);
00572
00573 default:
00574 return -ENOTTY;
00575 }
00576
00577 return 0;
00578 }
00579
00590 static ssize_t most_sync_rt_read(struct rtdm_dev_context *context,
00591 rtdm_user_info_t *user_info,
00592 void *buff,
00593 size_t count)
00594 {
00595 struct most_sync_rt_file *file = (void *)context->dev_private;
00596 struct most_sync_rt_dev *sync_dev = file->sync_dev;
00597 struct rtnrt_memcopy_desc copy = { rtnrt_copy_to_user_rt, (void *)user_info };
00598 ssize_t copied = 0;
00599 int err = 0;
00600
00601 pr_sync_debug(PR "Entering most_sync_rt_read %d, c=%d\n",
00602 file->reader_index, count);
00603
00604
00605 return_value_if_fails(count != 0, 0);
00606
00607
00608 if (!file->rx_running) {
00609 rtnrt_err(PR "Cannot read at this time\n");
00610 return -EBUSY;
00611 }
00612
00613
00614 err = most_sync_rt_read_write_begin(&sync_dev->rx_sync);
00615 if (err < 0) {
00616 pr_sync_debug(PR "most_sync_rt_read_write_begin "
00617 "returned %d\n", err);
00618 return err;
00619 }
00620
00621 while (copied == 0) {
00622 copied = rxbuf_get(sync_dev->sw_receive_buf, file->reader_index,
00623 file->part_rx, buff, count, ©);
00624
00625 if (unlikely(copied < 0)) {
00626 rtnrt_err(PR "Error in rxbuf_get: %d\n", copied);
00627 goto out_read;
00628 }
00629
00630 if (copied == 0) {
00631 RTDM_EXECUTE_ATOMICALLY(
00632 if (rxbuf_is_empty(sync_dev->sw_receive_buf, file->reader_index))
00633 err = rtdm_event_wait(&sync_dev->rx_wait);
00634 );
00635
00636 if (unlikely(err != 0)) {
00637 pr_sync_debug(PR "rtdm_event_wait returned with %d\n", err);
00638 copied = err;
00639 goto out_read;
00640 }
00641 }
00642 }
00643
00644 out_read:
00645 most_sync_rt_read_write_end(&sync_dev->rx_sync);
00646
00647 pr_sync_debug(PR "Finishing most_sync_rt_read %d with %d\n",
00648 file->reader_index, copied);
00649 return copied;
00650 }
00651
00662 static ssize_t most_sync_rt_write(struct rtdm_dev_context *context,
00663 rtdm_user_info_t *user_info,
00664 const void *buff,
00665 size_t count)
00666 {
00667 struct most_sync_rt_file *file = (void *)context->dev_private;
00668 struct most_sync_rt_dev *sync_dev = file->sync_dev;
00669 struct rtnrt_memcopy_desc copy = { rtnrt_copy_from_user_rt, (void *)user_info };
00670 ssize_t copied = 0;
00671 int err = 0;
00672
00673 pr_sync_debug(PR "Write called, count = %d\n", count);
00674
00675
00676 return_value_if_fails(count != 0, 0);
00677
00678
00679 if (!file->tx_running) {
00680 rtnrt_err(PR "Cannot write at this time\n");
00681 return -EBUSY;
00682 }
00683
00684
00685 err = most_sync_rt_read_write_begin(&sync_dev->tx_sync);
00686 if (err < 0) {
00687 pr_sync_debug(PR "most_sync_rt_read_write_begin returned %d", err);
00688 return err;
00689 }
00690
00691 while (copied != count) {
00692 err = txbuf_put(sync_dev->sw_transmit_buf, file->writer_index,
00693 file->part_tx, buff + copied, count - copied, ©);
00694 if (unlikely(err < 0)) {
00695 rtnrt_err(PR "Error in txbuf_put: %d\n", err);
00696 goto out_write;
00697 }
00698
00699 copied += err;
00700 if (err == 0) {
00701 RTDM_EXECUTE_ATOMICALLY(
00702 if (txbuf_is_full(sync_dev->sw_transmit_buf, file->writer_index))
00703 err = rtdm_event_wait(&sync_dev->tx_wait);
00704 );
00705
00706 if (unlikely(err != 0)) {
00707 pr_sync_debug(PR "rtdm_event_wait returned with %d\n", err);
00708 copied = err;
00709 goto out_write;
00710 }
00711 }
00712 }
00713
00714 out_write:
00715 most_sync_rt_read_write_end(&sync_dev->tx_sync);
00716 pr_sync_debug(PR "Finishing most_sync_write %d with %d\n",
00717 file->writer_index, copied);
00718 return copied;
00719 }
00720
00727 static int most_sync_rt_probe(struct most_dev *most_dev)
00728 {
00729 int number = MOST_DEV_CARDNUMBER(most_dev);
00730 int err;
00731 struct most_sync_rt_dev *sync_dev;
00732
00733 return_value_if_fails_dbg(number < MOST_DEVICE_NUMBER, -EINVAL);
00734 pr_sync_debug(PR "most_sync_rt_probe called, registering %d\n", number);
00735
00736
00737 sync_dev = kmalloc(sizeof(struct most_sync_rt_dev), GFP_KERNEL);
00738 if (unlikely(sync_dev == NULL)) {
00739 rtnrt_warn(PR "Allocation of private data structure failed\n");
00740 err = -ENOMEM;
00741 goto out;
00742 }
00743 memset(sync_dev, 0, sizeof(struct most_sync_rt_dev));
00744
00745
00746 sync_dev->most_dev = most_dev;
00747 INIT_LIST_HEAD(&sync_dev->file_list);
00748 rtdm_lock_init(&sync_dev->lock);
00749 rtdm_event_init(&sync_dev->rx_wait, 0);
00750 rtdm_event_init(&sync_dev->tx_wait, 0);
00751 most_conf_sync_init(&sync_dev->tx_sync);
00752 most_conf_sync_init(&sync_dev->rx_sync);
00753 atomic_set(&sync_dev->receiver_count, 0);
00754 atomic_set(&sync_dev->transmitter_count, 0);
00755
00756
00757 memcpy(&sync_dev->rtdm_dev, &device_templ, sizeof(struct rtdm_device));
00758 snprintf(sync_dev->rtdm_dev.device_name, RTDM_MAX_DEVNAME_LEN,
00759 "mostsync%d", number);
00760 sync_dev->rtdm_dev.device_id = number;
00761 sync_dev->rtdm_dev.proc_name = sync_dev->rtdm_dev.device_name;
00762
00763
00764 err = rtdm_dev_register(&sync_dev->rtdm_dev);
00765 if (unlikely(err < 0)) {
00766 goto out_sync_dev;
00767 }
00768
00769
00770 most_sync_rt_devices[number] = sync_dev;
00771
00772 return 0;
00773
00774 out_sync_dev:
00775 kfree(sync_dev);
00776 out:
00777
00778 return err;
00779 }
00780
00787 static int most_sync_rt_remove(struct most_dev *dev)
00788 {
00789 int number = MOST_DEV_CARDNUMBER(dev);
00790 struct most_sync_rt_dev *sync_dev = most_sync_rt_devices[number];
00791
00792 pr_sync_debug(PR "most_sync_rt_remove called, unregistering %d\n", number);
00793
00794
00795 rtdm_dev_unregister(&sync_dev->rtdm_dev, 1000);
00796
00797
00798 most_sync_rt_devices[number] = NULL;
00799 rtdm_event_destroy(&sync_dev->rx_wait);
00800 rtdm_event_destroy(&sync_dev->tx_wait);
00801 most_conf_sync_destroy(&sync_dev->rx_sync);
00802 most_conf_sync_destroy(&sync_dev->tx_sync);
00803
00804 kfree(sync_dev);
00805
00806 return 0;
00807 }
00808
00815 static void most_sync_rt_interrupt_handler(struct most_dev *dev,
00816 unsigned int intstatus)
00817 {
00818 int card = MOST_DEV_CARDNUMBER(dev);
00819 struct most_sync_rt_dev *sync_dev = most_sync_rt_devices[card];
00820 u32 val;
00821 int current_page;
00822
00823 return_if_fails_dbg(sync_dev != NULL);
00824
00825 if (intstatus & ISSRX) {
00826 void *dma_start;
00827 size_t siz;
00828
00829 pr_rt_irq_debug(PR "RT RX INT\n");
00830
00831 val = most_readreg_rt(sync_dev->most_dev, MOST_PCI_SRXCTRL_REG);
00832 dma_start = sync_dev->hw_receive_buf.addr_virt;
00833 siz = sync_dev->hw_receive_buf.size / 2;
00834
00835
00836
00837
00838
00839 if (!(val & SRXPP)) {
00840 dma_start += siz;
00841 }
00842
00843 measuring_receive_isr_start(sync_dev->sw_receive_buf);
00844 rxbuf_put(sync_dev->sw_receive_buf, dma_start, siz);
00845 measuring_receive_isr_wakeup();
00846 rtdm_event_pulse(&sync_dev->rx_wait);
00847
00848 current_page = (val & SRXPP) ? 1 : 2;
00849 if ((sync_dev->rx_current_page != 0) &&
00850 (sync_dev->rx_current_page == current_page)) {
00851 rtnrt_warn(PR "RT-RX: sync_dev->rx_current_page == current_page\n");
00852 }
00853 sync_dev->rx_current_page = current_page;
00854 }
00855
00856 if (intstatus & ISSTX) {
00857 void *dma_start;
00858 ssize_t read;
00859 size_t siz;
00860 unsigned int *ptr;
00861
00862 pr_rt_irq_debug(PR "TX RT INT\n");
00863
00864 val = most_readreg_rt(sync_dev->most_dev, MOST_PCI_STXCTRL_REG);
00865 dma_start = sync_dev->hw_transmit_buf.addr_virt;
00866 siz = sync_dev->hw_transmit_buf.size / 2;
00867
00868
00869
00870
00871
00872 if (!(val & STXPP)) {
00873 dma_start += siz;
00874 }
00875
00876 ptr = dma_start;
00877
00878 read = txbuf_get(sync_dev->sw_transmit_buf, dma_start, siz);
00879 rtdm_event_pulse(&sync_dev->tx_wait);
00880
00881 current_page = (val & STXPP) ? 1 : 2;
00882 if ((sync_dev->tx_current_page != 0) &&
00883 (sync_dev->tx_current_page == current_page))
00884 {
00885 rtnrt_warn(PR "RT-TX: sync_dev->tx_current_page == current_page\n");
00886 }
00887 sync_dev->tx_current_page = current_page;
00888 }
00889 }
00890
00895 static struct most_high_driver most_sync_rt_high_driver = {
00896 .name = "most-sync-rt",
00897 .sema_list = LIST_HEAD_INIT(most_sync_rt_high_driver.sema_list),
00898 .spin_list = LIST_HEAD_INIT(most_sync_rt_high_driver.spin_list),
00899 .probe = most_sync_rt_probe,
00900 .remove = most_sync_rt_remove,
00901 .interrupt_mask = (IESTX | IESRX),
00902 .int_handler = most_sync_rt_interrupt_handler
00903 };
00904
00910 static int __init most_sync_rt_init(void)
00911 {
00912 int err;
00913
00914 rtnrt_info("Loading module %s, version %s\n", DRIVER_NAME, version);
00915 print_measuring_warning();
00916
00917 serial_rt_debug_init();
00918
00919
00920 err = most_register_high_driver(&most_sync_rt_high_driver);
00921 if (unlikely(err != 0)) {
00922 return err;
00923 }
00924
00925 return 0;
00926 }
00927
00931 static void __exit most_sync_rt_exit(void)
00932 {
00933 most_deregister_high_driver(&most_sync_rt_high_driver);
00934 serial_rt_debug_finish();
00935
00936 rtnrt_info("Unloading module %s, version %s\n", DRIVER_NAME, version);
00937 }
00938
00939 #ifndef DOXYGEN
00940 EXPORT_SYMBOL(hw_tx_buffer_size);
00941 EXPORT_SYMBOL(hw_rx_buffer_size);
00942 EXPORT_SYMBOL(sw_tx_buffer_size);
00943 EXPORT_SYMBOL(sw_rx_buffer_size);
00944
00945 MODULE_LICENSE("GPL");
00946 MODULE_AUTHOR("Bernhard Walle");
00947 MODULE_VERSION("$Rev: 170 $");
00948 MODULE_DESCRIPTION("Real-time (RTDM) Driver for MOST Synchronous data.");
00949 module_init(most_sync_rt_init);
00950 module_exit(most_sync_rt_exit);
00951 #endif
00952
00953