static int ni_pcidio_cmd(struct comedi_device *dev, struct comedi_subdevice *s) { struct comedi_cmd *cmd = &s->async->cmd; writel(0x0000, devpriv->mite->daq_io_addr + Port_Pin_Directions(0)); if (1) { writeb(0x0f, devpriv->mite->daq_io_addr + Data_Path); writeb(TransferWidth(0) | TransferLength(0), devpriv->mite->daq_io_addr + Transfer_Size_Control); } else { writeb(0x03, devpriv->mite->daq_io_addr + Data_Path); writeb(TransferWidth(3) | TransferLength(0), devpriv->mite->daq_io_addr + Transfer_Size_Control); } if (cmd->scan_begin_src == TRIG_TIMER) { writeb(0, devpriv->mite->daq_io_addr + OpMode); writeb(0x00, devpriv->mite->daq_io_addr + ClockReg); writeb(1, devpriv->mite->daq_io_addr + Sequence); writeb(0x04, devpriv->mite->daq_io_addr + ReqReg); writeb(4, devpriv->mite->daq_io_addr + BlockMode); writeb(3, devpriv->mite->daq_io_addr + LinePolarities); writeb(0xc0, devpriv->mite->daq_io_addr + AckSer); writel(ni_pcidio_ns_to_timer(&cmd->scan_begin_arg, TRIG_ROUND_NEAREST), devpriv->mite->daq_io_addr + StartDelay); writeb(1, devpriv->mite->daq_io_addr + ReqDelay); writeb(1, devpriv->mite->daq_io_addr + ReqNotDelay); writeb(1, devpriv->mite->daq_io_addr + AckDelay); writeb(0x0b, devpriv->mite->daq_io_addr + AckNotDelay); writeb(0x01, devpriv->mite->daq_io_addr + Data1Delay); writew(0, devpriv->mite->daq_io_addr + ClockSpeed); writeb(0, devpriv->mite->daq_io_addr + DAQOptions); } else { writeb(0, devpriv->mite->daq_io_addr + OpMode); writeb(0x00, devpriv->mite->daq_io_addr + ClockReg); writeb(0, devpriv->mite->daq_io_addr + Sequence); writeb(0x00, devpriv->mite->daq_io_addr + ReqReg); writeb(4, devpriv->mite->daq_io_addr + BlockMode); writeb(0, devpriv->mite->daq_io_addr + LinePolarities); writeb(0x00, devpriv->mite->daq_io_addr + AckSer); writel(1, devpriv->mite->daq_io_addr + StartDelay); writeb(1, devpriv->mite->daq_io_addr + ReqDelay); writeb(1, devpriv->mite->daq_io_addr + ReqNotDelay); writeb(1, devpriv->mite->daq_io_addr + AckDelay); writeb(0x0C, devpriv->mite->daq_io_addr + AckNotDelay); writeb(0x10, devpriv->mite->daq_io_addr + Data1Delay); writew(0, devpriv->mite->daq_io_addr + ClockSpeed); writeb(0x60, devpriv->mite->daq_io_addr + DAQOptions); } if (cmd->stop_src == TRIG_COUNT) { writel(cmd->stop_arg, devpriv->mite->daq_io_addr + Transfer_Count); } else { } #ifdef USE_DMA writeb(ClearPrimaryTC | ClearSecondaryTC, devpriv->mite->daq_io_addr + Group_1_First_Clear); { int retval = setup_mite_dma(dev, s); if (retval) return retval; } #else writeb(0x00, devpriv->mite->daq_io_addr + DMA_Line_Control_Group1); #endif writeb(0x00, devpriv->mite->daq_io_addr + DMA_Line_Control_Group2); writeb(0xff, devpriv->mite->daq_io_addr + Group_1_First_Clear); writeb(IntEn, devpriv->mite->daq_io_addr + Interrupt_Control); writeb(0x03, devpriv->mite->daq_io_addr + Master_DMA_And_Interrupt_Control); if (cmd->stop_src == TRIG_NONE) { devpriv->OpModeBits = DataLatching(0) | RunMode(7); } else { devpriv->OpModeBits = Numbered | RunMode(7); } if (cmd->start_src == TRIG_NOW) { writeb(devpriv->OpModeBits, devpriv->mite->daq_io_addr + OpMode); s->async->inttrig = NULL; } else { s->async->inttrig = ni_pcidio_inttrig; } DPRINTK("ni_pcidio: command started\n"); return 0; }
static int ni_pcidio_cmd(struct comedi_device *dev, struct comedi_subdevice *s) { struct comedi_cmd *cmd = &s->async->cmd; /* XXX configure ports for input */ writel(0x0000, devpriv->mite->daq_io_addr + Port_Pin_Directions(0)); if (1) { /* enable fifos A B C D */ writeb(0x0f, devpriv->mite->daq_io_addr + Data_Path); /* set transfer width a 32 bits */ writeb(TransferWidth(0) | TransferLength(0), devpriv->mite->daq_io_addr + Transfer_Size_Control); } else { writeb(0x03, devpriv->mite->daq_io_addr + Data_Path); writeb(TransferWidth(3) | TransferLength(0), devpriv->mite->daq_io_addr + Transfer_Size_Control); } /* protocol configuration */ if (cmd->scan_begin_src == TRIG_TIMER) { /* page 4-5, "input with internal REQs" */ writeb(0, devpriv->mite->daq_io_addr + OpMode); writeb(0x00, devpriv->mite->daq_io_addr + ClockReg); writeb(1, devpriv->mite->daq_io_addr + Sequence); writeb(0x04, devpriv->mite->daq_io_addr + ReqReg); writeb(4, devpriv->mite->daq_io_addr + BlockMode); writeb(3, devpriv->mite->daq_io_addr + LinePolarities); writeb(0xc0, devpriv->mite->daq_io_addr + AckSer); writel(ni_pcidio_ns_to_timer(&cmd->scan_begin_arg, TRIG_ROUND_NEAREST), devpriv->mite->daq_io_addr + StartDelay); writeb(1, devpriv->mite->daq_io_addr + ReqDelay); writeb(1, devpriv->mite->daq_io_addr + ReqNotDelay); writeb(1, devpriv->mite->daq_io_addr + AckDelay); writeb(0x0b, devpriv->mite->daq_io_addr + AckNotDelay); writeb(0x01, devpriv->mite->daq_io_addr + Data1Delay); /* manual, page 4-5: ClockSpeed comment is incorrectly listed * on DAQOptions */ writew(0, devpriv->mite->daq_io_addr + ClockSpeed); writeb(0, devpriv->mite->daq_io_addr + DAQOptions); } else { /* TRIG_EXT */ /* page 4-5, "input with external REQs" */ writeb(0, devpriv->mite->daq_io_addr + OpMode); writeb(0x00, devpriv->mite->daq_io_addr + ClockReg); writeb(0, devpriv->mite->daq_io_addr + Sequence); writeb(0x00, devpriv->mite->daq_io_addr + ReqReg); writeb(4, devpriv->mite->daq_io_addr + BlockMode); writeb(0, devpriv->mite->daq_io_addr + LinePolarities); writeb(0x00, devpriv->mite->daq_io_addr + AckSer); writel(1, devpriv->mite->daq_io_addr + StartDelay); writeb(1, devpriv->mite->daq_io_addr + ReqDelay); writeb(1, devpriv->mite->daq_io_addr + ReqNotDelay); writeb(1, devpriv->mite->daq_io_addr + AckDelay); writeb(0x0C, devpriv->mite->daq_io_addr + AckNotDelay); writeb(0x10, devpriv->mite->daq_io_addr + Data1Delay); writew(0, devpriv->mite->daq_io_addr + ClockSpeed); writeb(0x60, devpriv->mite->daq_io_addr + DAQOptions); } if (cmd->stop_src == TRIG_COUNT) { writel(cmd->stop_arg, devpriv->mite->daq_io_addr + Transfer_Count); } else { /* XXX */ } #ifdef USE_DMA writeb(ClearPrimaryTC | ClearSecondaryTC, devpriv->mite->daq_io_addr + Group_1_First_Clear); { int retval = setup_mite_dma(dev, s); if (retval) return retval; } #else writeb(0x00, devpriv->mite->daq_io_addr + DMA_Line_Control_Group1); #endif writeb(0x00, devpriv->mite->daq_io_addr + DMA_Line_Control_Group2); /* clear and enable interrupts */ writeb(0xff, devpriv->mite->daq_io_addr + Group_1_First_Clear); /* writeb(ClearExpired, devpriv->mite->daq_io_addr+Group_1_Second_Clear); */ writeb(IntEn, devpriv->mite->daq_io_addr + Interrupt_Control); writeb(0x03, devpriv->mite->daq_io_addr + Master_DMA_And_Interrupt_Control); if (cmd->stop_src == TRIG_NONE) { devpriv->OpModeBits = DataLatching(0) | RunMode(7); } else { /* TRIG_TIMER */ devpriv->OpModeBits = Numbered | RunMode(7); } if (cmd->start_src == TRIG_NOW) { /* start */ writeb(devpriv->OpModeBits, devpriv->mite->daq_io_addr + OpMode); s->async->inttrig = NULL; } else { /* TRIG_INT */ s->async->inttrig = ni_pcidio_inttrig; } DPRINTK("ni_pcidio: command started\n"); return 0; }
static int ni_pcidio_cmdtest(struct comedi_device *dev, struct comedi_subdevice *s, struct comedi_cmd *cmd) { int err = 0; int tmp; tmp = cmd->start_src; cmd->start_src &= TRIG_NOW | TRIG_INT; if (!cmd->start_src || tmp != cmd->start_src) err++; tmp = cmd->scan_begin_src; cmd->scan_begin_src &= TRIG_TIMER | TRIG_EXT; if (!cmd->scan_begin_src || tmp != cmd->scan_begin_src) err++; tmp = cmd->convert_src; cmd->convert_src &= TRIG_NOW; if (!cmd->convert_src || tmp != cmd->convert_src) err++; tmp = cmd->scan_end_src; cmd->scan_end_src &= TRIG_COUNT; if (!cmd->scan_end_src || tmp != cmd->scan_end_src) err++; tmp = cmd->stop_src; cmd->stop_src &= TRIG_COUNT | TRIG_NONE; if (!cmd->stop_src || tmp != cmd->stop_src) err++; if (err) return 1; if (cmd->start_src != TRIG_NOW && cmd->start_src != TRIG_INT) err++; if (cmd->scan_begin_src != TRIG_TIMER && cmd->scan_begin_src != TRIG_EXT) err++; if (err) return 2; if (cmd->start_arg != 0) { cmd->start_arg = 0; err++; } #define MAX_SPEED (TIMER_BASE) if (cmd->scan_begin_src == TRIG_TIMER) { if (cmd->scan_begin_arg < MAX_SPEED) { cmd->scan_begin_arg = MAX_SPEED; err++; } } else { if (cmd->scan_begin_arg != 0) { cmd->scan_begin_arg = 0; err++; } } if (cmd->convert_arg != 0) { cmd->convert_arg = 0; err++; } if (cmd->scan_end_arg != cmd->chanlist_len) { cmd->scan_end_arg = cmd->chanlist_len; err++; } if (cmd->stop_src == TRIG_COUNT) { } else { if (cmd->stop_arg != 0) { cmd->stop_arg = 0; err++; } } if (err) return 3; if (cmd->scan_begin_src == TRIG_TIMER) { tmp = cmd->scan_begin_arg; ni_pcidio_ns_to_timer(&cmd->scan_begin_arg, cmd->flags & TRIG_ROUND_MASK); if (tmp != cmd->scan_begin_arg) err++; } if (err) return 4; return 0; }
static int ni_pcidio_cmdtest(struct comedi_device *dev, struct comedi_subdevice *s, struct comedi_cmd *cmd) { int err = 0; int tmp; /* step 1: make sure trigger sources are trivially valid */ tmp = cmd->start_src; cmd->start_src &= TRIG_NOW | TRIG_INT; if (!cmd->start_src || tmp != cmd->start_src) err++; tmp = cmd->scan_begin_src; cmd->scan_begin_src &= TRIG_TIMER | TRIG_EXT; if (!cmd->scan_begin_src || tmp != cmd->scan_begin_src) err++; tmp = cmd->convert_src; cmd->convert_src &= TRIG_NOW; if (!cmd->convert_src || tmp != cmd->convert_src) err++; tmp = cmd->scan_end_src; cmd->scan_end_src &= TRIG_COUNT; if (!cmd->scan_end_src || tmp != cmd->scan_end_src) err++; tmp = cmd->stop_src; cmd->stop_src &= TRIG_COUNT | TRIG_NONE; if (!cmd->stop_src || tmp != cmd->stop_src) err++; if (err) return 1; /* step 2: make sure trigger sources are unique and mutually compatible */ /* note that mutual compatibility is not an issue here */ if (cmd->start_src != TRIG_NOW && cmd->start_src != TRIG_INT) err++; if (cmd->scan_begin_src != TRIG_TIMER && cmd->scan_begin_src != TRIG_EXT) err++; if (err) return 2; /* step 3: make sure arguments are trivially compatible */ if (cmd->start_arg != 0) { /* same for both TRIG_INT and TRIG_NOW */ cmd->start_arg = 0; err++; } #define MAX_SPEED (TIMER_BASE) /* in nanoseconds */ if (cmd->scan_begin_src == TRIG_TIMER) { if (cmd->scan_begin_arg < MAX_SPEED) { cmd->scan_begin_arg = MAX_SPEED; err++; } /* no minimum speed */ } else { /* TRIG_EXT */ /* should be level/edge, hi/lo specification here */ if (cmd->scan_begin_arg != 0) { cmd->scan_begin_arg = 0; err++; } } if (cmd->convert_arg != 0) { cmd->convert_arg = 0; err++; } if (cmd->scan_end_arg != cmd->chanlist_len) { cmd->scan_end_arg = cmd->chanlist_len; err++; } if (cmd->stop_src == TRIG_COUNT) { /* no limit */ } else { /* TRIG_NONE */ if (cmd->stop_arg != 0) { cmd->stop_arg = 0; err++; } } if (err) return 3; /* step 4: fix up any arguments */ if (cmd->scan_begin_src == TRIG_TIMER) { tmp = cmd->scan_begin_arg; ni_pcidio_ns_to_timer(&cmd->scan_begin_arg, cmd->flags & TRIG_ROUND_MASK); if (tmp != cmd->scan_begin_arg) err++; } if (err) return 4; return 0; }