A counter is an input device, "counting" the number of triggers that occur while the gate is enabled. A timer is an output device. counter "command" { unsigned int mode; unsigned int src1_src; unsigned int src1_arg; unsigned int src2_src; unsigned int src2_arg; unsigned int gate_src; unsigned int gate_arg; } Counter examples: (Unless otherwise specified, _src's are TRIG_NONE.) Counting up at a rate of 1/ms: mode = UP_COUNTER; src1_src = TRIG_TIMER; src1_arg = 1000000; Counting down at a rate of 1/ms: mode = DOWN_COUNTER; arg1_src = TRIG_TIMER; arg1_arg = 1000000; Counting up at each rising transition of digital input 4: mode = UP_COUNTER; src1_src = TRIG_EXT; src1_arg = 4 | TRIG_EXT_RISING; Quadrature counting on di 0,1: mode = QUADRATURE; src1_src = TRIG_EXT; src1_arg = 0; src2_src = TRIG_EXT; src1_arg = 1; Interval timing of digital input 4: Counter setup: mode = UP_COUNTER; src1_src = TRIG_TIMER; gate_src = TRIG_EXT; gate_arg = 4 | LEVEL_1; event_src = TRIG_EXT; event_arg = 4 | FALLING_EDGE; flags = COUNT_RESET; /* counter resets at every event */ Command setup: start_src = TRIG_NOW; scan_begin_src = TRIG_NOW; convert_src = TRIG_FOLLOW; scan_end_src = TRIG_COUNT; scan_end_arg = 1; stop_src = whatever; Timer examples: Counters are based on a number of digital inputs, typically 2 or 3, and the count is changed due to the transition of one line and the status of other lines. In the most generic sense, the digital inputs define a particular state, and transitions between different states are mapped to either increment, decrement, or not change the counter. A fourth option is to trigger an exception. For example, in the case of 3 digital inputs, the transition 000->010 might be mapped to +1, to increment a counter. The other possible transitions (there are (2^3)*(2^3)=64 total) would be similarily mapped. An extension to this is to define that some transitions cause the current counter value to be pushed into a FIFO, to be read like asynchronous input. This would be in parallel to other functions. Most hardware does not allow this kind of programming flexibility. A typical hardware device will only allow transitions on one channel to change the counter, although other channels may affect the amount that the counter is changed. One idea: Counters are based on 1,2, or 3 digital inputs, and the count is based on transitions between the inputs. A particular counting mode can be specified by linking transitions to a value to be added to the counter. For the case of 1 input, you essentially have two possible (non-trivial) counters: Up counter on rising edge: 0->1 +1 1->0 0 Down counter on rising edge: 0->1 -1 1->0 0 (and the trailing edge counterparts) 2 inputs: possible transitions: 00->01 00->10 00->11 01->00 01->10 01->11 10->00 10->01 10->11 11->00 11->01 11->10 if we limit ourselves to 1-bit transitions, we only have: 00->01 00->10 01->00 01->11 10->00 10->11 11->01 11->10 Example: an up counter on rising edge of x1 with enable on 1x: 00->01 0 00->10 0 01->00 0 01->11 0 10->00 0 10->11 1 11->01 0 11->10 0 Example: up/down counter on rising edge, 1x is up, 0x is down 00->01 0 00->10 -1 01->00 0 01->11 0 10->00 0 10->11 1 11->01 0 11->10 0 Example: quadrature counter, up is CCW 01 00 11 10 00->01 1 00->10 -1 01->00 -1 01->11 1 10->00 1 10->11 -1 11->01 -1 11->10 1 Additionally, we might have an additional bit that means "latch and add to fifo" and/or interrupt. Probably need to be able to specify input routing. Need a way to specify invalid transitions. Possibly specify reset bit (?) Examples from STC spec: Simple event counting - sync, ok Simple gated-event counting - sync, ok buffered non-cumulative event counting - async, ok buffered cumulative event counting - async, ok relative position sensing (up/down) - sync, ok single period measurement - single pulse-width measurement - buffered period measurement - buffered semi-period measurement - buffered pulse-width measurement -