Converted comedilib docs to docbook-xml 4.4, fixing a bunch of

parse errors along the way (mostly unclosed tags).
This commit is contained in:
Frank Mori Hess 2008-01-24 01:32:41 +00:00
parent a06bba542a
commit a0568092e7
14 changed files with 367 additions and 374 deletions

View file

@ -127,36 +127,14 @@ AM_CONDITIONAL(BUILD_SCXI, [test "$ENABLE_SCXI" == "yes"])
AC_ARG_ENABLE([docbook],[ --disable-docbook-binding Disable docbook],[ENABLE_DOCBOOK=$enableval],[ENABLE_DOCBOOK="yes"])
if test "$ENABLE_DOCBOOK" == "yes"; then
AC_PATH_PROG(DOCBOOK2MAN, docbook2man, no)
if test "$DOCBOOK2MAN" = "no" ; then
AC_MSG_WARN([docbook2man not found, will not be able to rebuild man pages])
AC_PATH_PROG(XMLTO, xmlto, no)
if test "$XMLTO" = "no" ; then
AC_MSG_WARN([xmlto not found, will not be able to rebuild documentation])
fi
else
DOCBOOK2MAN="no"
XMLTO="no"
fi
AM_CONDITIONAL(HAVE_DOCBOOK2MAN, [test "$DOCBOOK2MAN" != "no"])
if test "$ENABLE_DOCBOOK" == "yes"; then
AC_PATH_PROG(DOCBOOK2PDF, docbook2pdf, no)
if test "$DOCBOOK2PDF" = "no" ; then
AC_MSG_WARN([docbook2pdf not found, will not be able to rebuild pdf documentation])
fi
else
DOCBOOK2PDF="no"
fi
AM_CONDITIONAL(HAVE_DOCBOOK2PDF, [test "$DOCBOOK2PDF" != "no"])
if test "$ENABLE_DOCBOOK" == "yes"; then
AC_PATH_PROG(DOCBOOK2HTML, docbook2html, no)
if test "$DOCBOOK2HTML" = "no" ; then
AC_MSG_WARN([docbook2html not found, will not be able to rebuild html documentation])
fi
else
DOCBOOK2HTML="no"
fi
AM_CONDITIONAL(HAVE_DOCBOOK2HTML, [test "$DOCBOOK2HTML" != "no"])
AM_CONDITIONAL(HAVE_XMLTO, [test "$XMLTO" != "no"])
pcmciadir="\${sysconfdir}/pcmcia"
AC_SUBST(pcmciadir)

View file

@ -1,40 +1,38 @@
SGML = calibration_funcref.sgml command_funcref.sgml dio_funcref.sgml \
deprecated_funcref.sgml error_funcref.sgml extensions_funcref.sgml \
drivers.sgml funcref.sgml glossary.sgml \
install.sgml intro.sgml other.sgml reference.sgml tutorial.sgml \
driverwriting.sgml comedilib.sgml
XML = calibration_funcref.xml command_funcref.xml dio_funcref.xml \
deprecated_funcref.xml error_funcref.xml extensions_funcref.xml \
drivers.xml funcref.xml glossary.xml \
install.xml intro.xml other.xml reference.xml tutorial.xml \
driverwriting.xml comedilib.xml
EXTRA_DIST = $(SGML) calibration_funcref.txt command_funcref.txt dio_funcref.txt \
EXTRA_DIST = $(XML) calibration_funcref.txt command_funcref.txt dio_funcref.txt \
deprecated_funcref.txt error_funcref.txt extensions_funcref.txt \
funcref mkref drivers.txt mkdr FAQ \
acq-seq.gif doc_html man
BUILT_SOURCES = calibration_funcref.sgml command_funcref.sgml dio_funcref.sgml \
deprecated_funcref.sgml error_funcref.sgml extensions_funcref.sgml \
funcref.sgml drivers.sgml
BUILT_SOURCES = calibration_funcref.xml command_funcref.xml dio_funcref.xml \
deprecated_funcref.xml error_funcref.xml extensions_funcref.xml \
funcref.xml drivers.xml
if HAVE_DOCBOOK2PDF
dist_pdf_DATA = comedilib.pdf
else
dist_pdf_DATA =
endif
if HAVE_DOCBOOK2HTML
if HAVE_XMLTO
all_html = $(srcdir)/doc_html
install_html = install_html
uninstall_html = uninstall_html
else
all_html =
install_html =
uninstall_html =
endif
if HAVE_DOCBOOK2MAN
#pdf output for xmlto is broken in debian etch
#dist_pdf_DATA = comedilib.pdf
dist_pdf_DATA =
all_man = $(srcdir)/man
install_man = install_man
uninstall_man = uninstall_man
else
all_html =
install_html =
uninstall_html =
dist_pdf_DATA =
all_man =
install_man =
uninstall_man =
@ -48,8 +46,8 @@ uninstall-local: $(uninstall_html) $(uninstall_man)
#named this doc_html to avoid phony html target that is automatically generated
#(at least by automake1.8)
$(srcdir)/doc_html: $(SGML)
{ $(DOCBOOK2HTML) -o $(srcdir)/doc_html $(srcdir)/comedilib.sgml && touch $(srcdir)/doc_html; } || { $(RM) -r $(srcdir)/doc_html; exit 1; }
$(srcdir)/doc_html: $(XML)
{ $(XMLTO) -o $(srcdir)/doc_html -m $(srcdir)/comedilib_html_config.xsl --skip-validation html $(srcdir)/comedilib.xml && touch $(srcdir)/doc_html; } || { $(RM) -r $(srcdir)/doc_html; exit 1; }
install_html:
$(mkdir_p) $(DESTDIR)$(htmldir)/html
@ -61,8 +59,8 @@ uninstall_html:
for each in $(srcdir)/doc_html/*.html $(srcdir)/*.gif ; do \
$(RM) $(DESTDIR)$(htmldir)/html/`basename $$each` ; done
$(srcdir)/man: $(SGML)
{ $(DOCBOOK2MAN) -o $(srcdir)/man $(srcdir)/comedilib.sgml && touch $(srcdir)/man; } || { $(RM) -r $(srcdir)/man; exit 1; }
$(srcdir)/man: $(XML)
{ $(XMLTO) -o $(srcdir)/man --skip-validation man $(srcdir)/comedilib.xml && touch $(srcdir)/man; } || { $(RM) -r $(srcdir)/man; exit 1; }
install_man:
$(mkdir_p) -m 755 $(DESTDIR)$(mandir)/man3
@ -72,32 +70,32 @@ install_man:
uninstall_man:
for each in `find $(srcdir)/man/ -name '*.3'`; do $(RM) $(DESTDIR)$(mandir)/man3/`basename $$each` ; done
comedilib.pdf: $(SGML)
$(DOCBOOK2PDF) -o $(srcdir) $(srcdir)/comedilib.sgml
comedilib.pdf: $(XML)
$(XMLTO) -o $(srcdir)/pdf --skip-validation pdf $(srcdir)/comedilib.xml
funcref.sgml: funcref mkref
$(srcdir)/mkref $(srcdir)/funcref >$(srcdir)/funcref.sgml
funcref.xml: funcref mkref
$(srcdir)/mkref $(srcdir)/funcref >$(srcdir)/funcref.xml
calibration_funcref.sgml: calibration_funcref.txt mkref
$(srcdir)/mkref $(srcdir)/calibration_funcref.txt >$(srcdir)/calibration_funcref.sgml
calibration_funcref.xml: calibration_funcref.txt mkref
$(srcdir)/mkref $(srcdir)/calibration_funcref.txt >$(srcdir)/calibration_funcref.xml
command_funcref.sgml: command_funcref.txt mkref
$(srcdir)/mkref $(srcdir)/command_funcref.txt >$(srcdir)/command_funcref.sgml
command_funcref.xml: command_funcref.txt mkref
$(srcdir)/mkref $(srcdir)/command_funcref.txt >$(srcdir)/command_funcref.xml
dio_funcref.sgml: dio_funcref.txt mkref
$(srcdir)/mkref $(srcdir)/dio_funcref.txt >$(srcdir)/dio_funcref.sgml
dio_funcref.xml: dio_funcref.txt mkref
$(srcdir)/mkref $(srcdir)/dio_funcref.txt >$(srcdir)/dio_funcref.xml
deprecated_funcref.sgml: deprecated_funcref.txt mkref
$(srcdir)/mkref $(srcdir)/deprecated_funcref.txt >$(srcdir)/deprecated_funcref.sgml
deprecated_funcref.xml: deprecated_funcref.txt mkref
$(srcdir)/mkref $(srcdir)/deprecated_funcref.txt >$(srcdir)/deprecated_funcref.xml
error_funcref.sgml: error_funcref.txt mkref
$(srcdir)/mkref $(srcdir)/error_funcref.txt >$(srcdir)/error_funcref.sgml
error_funcref.xml: error_funcref.txt mkref
$(srcdir)/mkref $(srcdir)/error_funcref.txt >$(srcdir)/error_funcref.xml
extensions_funcref.sgml: extensions_funcref.txt mkref
$(srcdir)/mkref $(srcdir)/extensions_funcref.txt >$(srcdir)/extensions_funcref.sgml
extensions_funcref.xml: extensions_funcref.txt mkref
$(srcdir)/mkref $(srcdir)/extensions_funcref.txt >$(srcdir)/extensions_funcref.xml
drivers.sgml: drivers.txt mkdr
$(srcdir)/mkdr $(srcdir)/drivers.txt >$(srcdir)/drivers.sgml
drivers.xml: drivers.txt mkdr
$(srcdir)/mkdr $(srcdir)/drivers.txt >$(srcdir)/drivers.xml
maintainer-clean-local:
$(RM) -r $(srcdir)/doc_html $(srcdir)/man

View file

@ -1,25 +1,11 @@
<!DOCTYPE article PUBLIC "-//OASIS//DTD DocBook V4.2//EN" [
<!ENTITY intro SYSTEM "intro.sgml">
<!ENTITY install SYSTEM "install.sgml">
<!ENTITY tutorial SYSTEM "tutorial.sgml">
<!ENTITY other SYSTEM "other.sgml">
<!ENTITY driverwriting SYSTEM "driverwriting.sgml">
<!ENTITY drivers SYSTEM "drivers.sgml">
<!ENTITY reference SYSTEM "reference.sgml">
<!ENTITY funcref SYSTEM "funcref.sgml">
<!ENTITY calibration-funcref SYSTEM "calibration_funcref.sgml">
<!ENTITY command-funcref SYSTEM "command_funcref.sgml">
<!ENTITY dio-funcref SYSTEM "dio_funcref.sgml">
<!ENTITY deprecated-funcref SYSTEM "deprecated_funcref.sgml">
<!ENTITY error-funcref SYSTEM "error_funcref.sgml">
<!ENTITY extensions-funcref SYSTEM "extensions_funcref.sgml">
<!ENTITY glossary SYSTEM "glossary.sgml">
<!ENTITY comedi "<acronym>Comedi</acronym>">
<!ENTITY uuml "ue">
<!ENTITY hellip "...">
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE article PUBLIC "-//OASIS//DTD DocBook XML V4.4//EN"
"http://www.oasis-open.org/docbook/xml/4.4/docbookx.dtd" [
<!ENTITY % comedilib_entities SYSTEM "comedilib.ent">
%comedilib_entities;
]>
<article>
<article xmlns:xi="http://www.w3.org/2001/XInclude">
<articleinfo>
<title>
Comedi
@ -64,9 +50,6 @@ handbook
<abstract>
<para>
<emphasis role="strong">Abstract</emphasis>
</para>
<para>
&comedi; is a free software project to interface
<emphasis>digital acquisition</emphasis> (DAQ) cards. It is the
combination of three complementary software items: (i) a generic,
@ -105,74 +88,14 @@ USA.
</articleinfo>
&intro;
&install;
&tutorial;
&other;
&driverwriting;
<section id="lowleveldrivers">
<title>
Low-level drivers
</title>
&drivers;
</section>
<section id="comedireference">
<title>
&comedi; Reference
</title>
<para>
Reference for
<link linkend="constantsmacros">constants and macros</link>,
<link linkend="datatypesstructures">data types and structures</link>,
and <link linkend="functionreference">functions</link>.
</para>
&reference;
<!-- </section> -->
<section id="functionreference">
<title>Functions</title>
<section>
<title>Core Functions</title>
&funcref;
</section>
<section>
<title>Asyncronous Commands</title>
&command-funcref;
</section>
<section>
<title>Calibration</title>
&calibration-funcref;
</section>
<section>
<title>Digital I/O</title>
&dio-funcref;
</section>
<section>
<title>Error Reporting</title>
&error-funcref;
</section>
<section>
<title>Extensions</title>
&extensions-funcref;
</section>
<section>
<title>Deprecated</title>
&deprecated-funcref;
</section>
</section>
</section>
&glossary;
<xi:include href="intro.xml"/>
<xi:include href="install.xml"/>
<xi:include href="tutorial.xml"/>
<xi:include href="other.xml"/>
<xi:include href="driverwriting.xml"/>
<xi:include href="drivers.xml"/>
<xi:include href="reference.xml"/>
<xi:include href="glossary.xml"/>
</article>

View file

@ -0,0 +1,11 @@
<?xml version='1.0'?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:fo="http://www.w3.org/1999/XSL/Format"
version="1.0">
<xsl:param name="use.id.as.filename" select="'1'"/>
<xsl:param name="admon.graphics" select="'1'"/>
<xsl:param name="admon.graphics.path"></xsl:param>
<xsl:param name="chunk.section.depth" select="1"></xsl:param>
<xsl:param name="generate.section.toc.level" select="4"></xsl:param>
<!-- <xsl:param name="html.stylesheet" select="'docbook.css'"/> -->
</xsl:stylesheet>

View file

@ -1,3 +1,10 @@
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE article PUBLIC "-//OASIS//DTD DocBook XML V4.4//EN"
"http://www.oasis-open.org/docbook/xml/4.4/docbookx.dtd" [
<!ENTITY % comedilib_entities SYSTEM "comedilib.ent">
%comedilib_entities;
]>
<section id="driverwriting">
<title>
Writing a &comedi; driver
@ -16,7 +23,7 @@ all solved lots of boring but indispensable infrastructural things,
such as: timers, management of which drivers
are active, memory management for drivers and buffers, wrapping
of RTOS-specific interfaces, interrupt handler management, general
error handling, the <filename role=directory>/proc</filename>
error handling, the <filename role="directory">/proc</filename>
interface, etc. So,
the device driver writers can concentrate on the interesting stuff:
implementing their specific interface card's DAQ functionalities.
@ -28,7 +35,7 @@ know the answers to the following questions:
<listitem>
<para>
How does the
How does the
<link linkend="userkernelhow">communication</link> between user space
and kernel space work?
</para>
@ -38,7 +45,7 @@ and kernel space work?
<para>
What functionality is provided by the
<link linkend="comedikernelgeneric">generic</link> kernel-space
&comedi; functions, and what must be provided for each
&comedi; functions, and what must be provided for each
<link linkend="boardspecific">specific new driver</link>?
</para>
</listitem>
@ -72,16 +79,16 @@ Communication user space-kernel space
<para>
In user space, you interact with the functions implemented in the
<filename role=directory>/usr/src/comedilib</filename> directory. Most
<filename role="directory">/usr/src/comedilib</filename> directory. Most
of the device driver core of the Comedilib library is found in
<filename role=directory>lib</filename> subdirectory.
<filename role="directory">lib</filename> subdirectory.
</para>
<para>
All user-space &comedi;
All user-space &comedi;
<link linkend="instructions">instructions</link> and
<link linkend="commandsstreaming">commands</link>
<link linkend="commandsstreaming">commands</link>
are transmitted to kernel space through a traditional
<function>ioctl</function> system call.
<function>ioctl</function> system call.
(See <filename>/usr/src/comedilib/lib/ioctl.c</filename>.)
The user space information command is <emphasis>encoded</emphasis> as
a number in the <function>ioctl</function> call, and decoded in the
@ -92,7 +99,7 @@ counterparts. This is done in the
the <function>ioctl</function> system call, interprets its contents,
and then calls the corresponding kernel space
<function>do_&hellip;_ioctl</function> function(s).
For example, a &comedi;
For example, a &comedi;
<link linkend="instructions">instruction</link> is further processed
by the <function>do_insn_ioctl()</function>function. (Which, in turn,
uses <function>parse_insn()</function> for further detailed processing.)
@ -129,11 +136,11 @@ and constants.
<listitem>
<para>
<filename>include/linux/comedi_rt.h</filename>:
all the real-time stuff, such as management of ISR in RTAI and
all the real-time stuff, such as management of ISR in RTAI and
RTLinux/Free, and spinlocks for atomic sections.
</para>
</listitem>
<listitem>
<para>
<filename>include/linux/comedilib.h</filename>: the header file for
@ -144,10 +151,10 @@ the kernel library of &comedi;.
</itemizedlist>
</para>
<para>
From all the relevant &comedi; device driver code that is found in the
<filename role=directory>/usr/src/comedi/comedi</filename> directory
From all the relevant &comedi; device driver code that is found in the
<filename role="directory">/usr/src/comedi/comedi</filename> directory
(<emphasis>if</emphasis> the &comedi; source has been installed in its
normal <filename role=directory>/usr/src/comedi</filename> location),
normal <filename role="directory">/usr/src/comedi</filename> location),
the <emphasis role="strong">generic</emphasis> functionality is
contained in two parts:
<itemizedlist>
@ -159,22 +166,22 @@ role="strong">infrastructural support</emphasis>.
From these <filename>C</filename> files, it's especially the
<filename>comedi_fops.c</filename> file that implements what makes
&comedi; into what people want to use it for: a library that has
solved 90% of the DAQ device driver efforts, once and for all.
solved 90% of the DAQ device driver efforts, once and for all.
</para>
</listitem>
<listitem>
<para>
For <emphasis role="strong">real-time</emphasis> applications,
the subdirectory <filename role=directory>kcomedilib</filename>
the subdirectory <filename role="directory">kcomedilib</filename>
implements an interface in the kernel that is similar to the &comedi;
interface accessible through the
interface accessible through the
<link linkend="functionreference">user-space Comedi library</link>.
</para>
<para>
There are some differences in what is possible and/or needed
in kernel space and in user space, so the functionalities offered in
<filename role=directory>kcomedilib</filename> are not an exact copy
<filename role="directory">kcomedilib</filename> are not an exact copy
of the user-space library. For example, locking, interrupt handling,
real-time execution, callback handling, etc., are only available in
kernel space.
@ -200,7 +207,7 @@ interacts with:
typedef struct comedi_lrange_struct <link linkend="comedilrange">comedi_lrange</link>;
typedef struct comedi_subdevice_struct <link linkend="comedisubdevice">comedi_subdevice</link>;
typedef struct comedi_device_struct <link linkend="comedidevice">comedi_device</link>:
typedef struct comedi_async_struct <link linkend="comediasync">comedi_async</link>
typedef struct comedi_async_struct <link linkend="comediasync">comedi_async</link>
typedef struct comedi_driver_struct <link linkend="comedidriver">comedi_driver</link>;
</programlisting>
They can be found in
@ -220,8 +227,8 @@ different meaning: they encode the interaction with the
<emphasis>hardware</emphasis>, not with the <emphasis>user</emphasis>.
</para>
<para>
However, the <link linkend="ref-type-comedi-insn">comedi_insn</link>
and <link linkend="ref-type-comedi-cmd">comedi_cmd</link>
However, the <link linkend="ref-type-comedi-insn">comedi_insn</link>
and <link linkend="ref-type-comedi-cmd">comedi_cmd</link>
data structures are shared between user space and kernel space: this
should come as no surprise, since these data structures contain all
information that the user-space program must transfer to the
@ -237,7 +244,7 @@ that stores the device driver information that is relevant at the
operating system level, and the data structure
<link linkend="comediasync">comedi_async</link> that stores the
information about all <emphasis>asynchronous</emphasis> activities
(interrupts, callbacks and events).
(interrupts, callbacks and events).
</para>
<section id="comedilrange">
@ -285,34 +292,34 @@ struct comedi_subdevice_struct{
<link linkend="ref-type-lsampl-t">lsampl_t</link> maxdata; /* if maxdata==0, use list */
<link linkend="ref-type-lsampl-t">lsampl_t</link> *maxdata_list; /* list is channel specific */
unsigned int flags;
unsigned int *flaglist;
<link linkend="comedilrange">comedi_lrange</link> *range_table;
<link linkend="comedilrange">comedi_lrange</link> **range_table_list;
unsigned int *chanlist; /* driver-owned chanlist (not used) */
int (*insn_read)(<link linkend="comedidevice">comedi_device</link> *,<link linkend="comedisubdevice">comedi_subdevice</link> *,<link linkend="ref-type-comedi-insn">comedi_insn</link> *,<link linkend="ref-type-lsampl-t">lsampl_t</link> *);
int (*insn_write)(<link linkend="comedidevice">comedi_device</link> *,<link linkend="comedisubdevice">comedi_subdevice</link> *,<link linkend="ref-type-comedi-insn">comedi_insn</link> *,<link linkend="ref-type-lsampl-t">lsampl_t</link> *);
int (*insn_bits)(<link linkend="comedidevice">comedi_device</link> *,<link linkend="comedisubdevice">comedi_subdevice</link> *,<link linkend="ref-type-comedi-insn">comedi_insn</link> *,<link linkend="ref-type-lsampl-t">lsampl_t</link> *);
int (*insn_config)(<link linkend="comedidevice">comedi_device</link> *,<link linkend="comedisubdevice">comedi_subdevice</link> *,<link linkend="ref-type-comedi-insn">comedi_insn</link> *,<link linkend="ref-type-lsampl-t">lsampl_t</link> *);
int (*do_cmd)(<link linkend="comedidevice">comedi_device</link> *,<link linkend="comedisubdevice">comedi_subdevice</link> *);
int (*do_cmdtest)(<link linkend="comedidevice">comedi_device</link> *,<link linkend="comedisubdevice">comedi_subdevice</link> *,<link linkend="ref-type-comedi-cmd">comedi_cmd</link> *);
int (*poll)(<link linkend="comedidevice">comedi_device</link> *,<link linkend="comedisubdevice">comedi_subdevice</link> *);
int (*cancel)(<link linkend="comedidevice">comedi_device</link> *,<link linkend="comedisubdevice">comedi_subdevice</link> *);
int (*buf_change)(<link linkend="comedidevice">comedi_device</link> *,<link linkend="comedisubdevice">comedi_subdevice</link> *s,unsigned long new_size);
void (*munge)(<link linkend="comedidevice">comedi_device</link> *, <link linkend="comedisubdevice">comedi_subdevice</link> *s, void *data, unsigned int num_bytes, unsigned int start_chan_index );
unsigned int state;
};
</programlisting>
The function pointers <function>(*insn_read)</function> &hellip;
<function>(*cancel)</function> .
offer (pointers to) the standardized
offer (pointers to) the standardized
<link linkend="functionreference">user-visible API</link>
that every subdevice should offer; every device driver has to fill
in these functions with their board-specific implementations.
@ -323,7 +330,7 @@ definition, not show up in the device driver data structures.)
The <function>buf_change()</function> and <function>munge()</function>
functions offer functionality that is not visible to the user and for
which the device driver writer must provide a board-specific
implementation:
implementation:
<function>buf_change()</function> is called when a change in the
data buffer requires handling; <function>munge()</function> transforms
different bit-representations of DAQ values, for example from
@ -352,23 +359,23 @@ struct comedi_device_struct{
int rt;
spinlock_t spinlock;
int in_request_module;
int n_subdevices;
<link linkend="comedisubdevice">comedi_subdevice</link> *subdevices;
int options[COMEDI_NDEVCONFOPTS];
/* dumb */
int iobase;
int irq;
<link linkend="comedisubdevice">comedi_subdevice</link> *read_subdev;
wait_queue_head_t read_wait;
<link linkend="comedisubdevice">comedi_subdevice</link> *write_subdev;
wait_queue_head_t write_wait;
struct fasync_struct *async_queue;
void (*open)(<link linkend="comedidevice">comedi_device</link> *dev);
void (*close)(<link linkend="comedidevice">comedi_device</link> *dev);
};
@ -385,7 +392,7 @@ struct comedi_device_struct{
<para>
The following data structure contains all relevant information:
addresses and sizes of buffers, pointers to the actual data, and the
information needed for
information needed for
<link linkend="drivercallbacks">event handling</link>:
<programlisting>
struct comedi_async_struct{
@ -394,30 +401,30 @@ struct comedi_async_struct{
unsigned long *buf_page_list; /* physical address of each page */
unsigned int max_bufsize; /* maximum buffer size, bytes */
unsigned int mmap_count; /* current number of mmaps of prealloc_buf */
volatile unsigned int buf_write_count; /* byte count for writer (write completed) */
volatile unsigned int buf_write_alloc_count; /* byte count for writer (allocated for writing) */
volatile unsigned int buf_read_count; /* byte count for reader (read completed)*/
unsigned int buf_write_ptr; /* buffer marker for writer */
unsigned int buf_read_ptr; /* buffer marker for reader */
unsigned int cur_chan; /* useless channel marker for interrupt */
/* number of bytes that have been received for current scan */
unsigned int scan_progress;
/* keeps track of where we are in chanlist as for munging */
unsigned int munge_chan;
unsigned int events; /* events that have occurred */
<link linkend="ref-type-comedi-cmd">comedi_cmd</link> cmd;
// callback stuff
unsigned int cb_mask;
int (*cb_func)(unsigned int flags,void *);
void *cb_arg;
int (*inttrig)(<link linkend="comedidevice">comedi_device</link> *dev,<link linkend="comedisubdevice">comedi_subdevice</link> *s,unsigned int x);
int (*inttrig)(<link linkend="comedidevice">comedi_device</link> *dev,<link linkend="comedisubdevice">comedi_subdevice</link> *s,unsigned int x);
};
</programlisting>
</para>
@ -460,7 +467,7 @@ Generic driver support functions
<para>
The directory
<filename role=directory>comedi</filename> contains a large set of
<filename role="directory">comedi</filename> contains a large set of
support functions. Some of the most important ones are given below.
</para>
<para>
@ -505,7 +512,7 @@ Board-specific functionality
</title>
<para>
The <filename role=directory>/usr/src/comedi/comedi/drivers</filename>
The <filename role="directory">/usr/src/comedi/comedi/drivers</filename>
subdirectory contains
the <emphasis role="strong">board-specific</emphasis> device driver
code. Each new card must get an entry in this directory.
@ -550,7 +557,7 @@ necessary <link linkend="driverdatastructures">data structures</link>,
all properties of a device and its subdevices are defined, and filled
in in the generic &comedi; data structures. As part of this, pointers
to the low level instructions being supported by the subdevice have to
be set, which define the basic functionality. In somewhat more detail,
be set, which define the basic functionality. In somewhat more detail,
the <function>mydriver_attach()</function> function must:
<itemizedlist>
@ -609,9 +616,9 @@ each sub-device and each channel must get appropriate data fields, and
an appropriate initialization. The good news, of course, is that
&comedi; provides the data structures and the defines that fit very
well with almost all DAQ functionalities found on interface cards.
These can be found in the
These can be found in the
<link linkend="comedikernelgeneric">header files</link> of the
<filename role=directory>/usr/src/comedi/include/linux/</filename>
<filename role="directory">/usr/src/comedi/include/linux/</filename>
directory.
</para>
<para>
@ -660,7 +667,7 @@ buffer to the card, and execute the appropriate output conversions.
</itemizedlist>
In some drivers, you want to catch interrupts, and/or want to use the
<link linkend="insn-inttrig">INSN_INTTRIG</link> instruction. In this
case, you must provide and register these
case, you must provide and register these
<link linkend="drivercallbacks">callback</link> functions.
</para>
<para>
@ -686,7 +693,7 @@ has set the acquisition in motion has returned before the acquisition
has finished (or even started). So, not only the acquired data must be
sent back to the user's buffer <quote>in the background</quote>, but
various types of asynchronous <emphasis>event handling</emphasis> can
be needed during the acquisition:
be needed during the acquisition:
<itemizedlist>
<listitem>
@ -730,17 +737,17 @@ The interrupt handlers are registered through the functions mentioned
The event handling is done in the existing &comedi; drivers in
statements such as this one:
<programlisting>
<anchor id="async-events">
<anchor id="async-events"/>
s->async->events |= COMEDI_CB_EOA | COMEDI_CB_ERROR
</programlisting>
It fills in the bits corresponding to particular events in the
It fills in the bits corresponding to particular events in the
<link linkend="comediasync">comedi_async</link> data structure.
The possible event bits are:
<itemizedlist>
<listitem>
<para>
<anchor id="comedi-cb-eoa">
<anchor id="comedi-cb-eoa"/>
<parameter>COMEDI_CB_EOA</parameter>: execute the callback at the
<quote>End Of-Acquisition</quote>.
</para>
@ -748,7 +755,7 @@ The possible event bits are:
<listitem>
<para>
<anchor id="comedi-cb-eos">
<anchor id="comedi-cb-eos"/>
<parameter>COMEDI_CB_EOS</parameter>: execute the callback at the
<quote>End-Of-Scan</quote>.
</para>
@ -756,7 +763,7 @@ The possible event bits are:
<listitem>
<para>
<anchor id="comedi-cb-overflow">
<anchor id="comedi-cb-overflow"/>
<parameter>COMEDI_CB_OVERFLOW</parameter>: execute the callback when a
buffer overflow has occurred.
</para>
@ -764,7 +771,7 @@ buffer overflow has occurred.
<listitem>
<para>
<anchor id="comedi-cb-error">
<anchor id="comedi-cb-error"/>
<parameter>COMEDI_CB_ERROR</parameter>: execute the callback at the
occurrence of an (undetermined) error.
</para>
@ -808,7 +815,7 @@ want to use your driver <emphasis>just</emphasis> to do digital I/O
and has no interrupts available.
</para>
</listitem>
<listitem>
<para>
Drivers are to have absolutely <emphasis role="strong">no</emphasis>
@ -819,7 +826,7 @@ to point to a structure containing any additional variables needed by
a driver/device combination.
</para>
</listitem>
<listitem>
<para>
Drivers should report errors and warnings via the
@ -856,11 +863,11 @@ that you call it <quote>mydriver.c</quote>
Put your new driver into <quote>comedi/drivers/mydriver.c</quote>.
</para>
</listitem>
<listitem>
<para>
Edit <quote>comedi/drivers/Makefile.am</quote> and add <quote>mydriver.ko</quote>
to the <quote>module_PROGRAMS</quote> list. Also add a line
to the <quote>module_PROGRAMS</quote> list. Also add a line
<programlisting>
mydriver_ko_SOURCES = mydriver.c
</programlisting>
@ -871,12 +878,12 @@ in the alphabetically appropriate place.
<listitem>
<para>
Run ./autogen.sh in the top-level comedi directory. You will
need to have (a recent version of) autoconf and automake
need to have (a recent version of) autoconf and automake
installed to successfully run autogen.sh. Afterwards, your driver will
be built along with the rest of the drivers when you 'make'.
</para>
</listitem>
<listitem>
<para>
If you want to have your driver included in the &comedi; distribution

View file

@ -298,7 +298,7 @@ Description:
<table COLSEP="1" ROWSEP="1" ORIENT="port" PGWIDE="1">
<title>subdevice flags</title>
<tgroup COLS="3" ALIGN="left" >
<tgroup cols="3" align="left" >
<thead>
<row>
<entry>Subdevice Flag</entry>

View file

@ -1,4 +1,9 @@
<!-- <!DOCTYPE section PUBLIC "-//OASIS//DTD DocBook V4.2//EN"> -->
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE article PUBLIC "-//OASIS//DTD DocBook XML V4.4//EN"
"http://www.oasis-open.org/docbook/xml/4.4/docbookx.dtd" [
<!ENTITY % comedilib_entities SYSTEM "comedilib.ent">
%comedilib_entities;
]>
<glossary id="comedilib-glossary">
<title>

View file

@ -1,4 +1,9 @@
<!-- <!DOCTYPE section PUBLIC "-//OASIS//DTD DocBook V4.2//EN"> -->
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE article PUBLIC "-//OASIS//DTD DocBook XML V4.4//EN"
"http://www.oasis-open.org/docbook/xml/4.4/docbookx.dtd" [
<!ENTITY % comedilib_entities SYSTEM "comedilib.ent">
%comedilib_entities;
]>
<section id="install">
<title>
@ -184,7 +189,7 @@ subdevices.
</para>
<para>
In the <filename role=directory>demo/</filename> directory, there is a
In the <filename role="directory">demo/</filename> directory, there is a
command called <command>info</command>, which provides information
about each subdevice on the board. Its output can be rather long,
if the board has several subdevices.

View file

@ -1,4 +1,9 @@
<!-- <!DOCTYPE section PUBLIC "-//OASIS//DTD DocBook V4.2//EN"> -->
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE article PUBLIC "-//OASIS//DTD DocBook XML V4.4//EN"
"http://www.oasis-open.org/docbook/xml/4.4/docbookx.dtd" [
<!ENTITY % comedilib_entities SYSTEM "comedilib.ent">
%comedilib_entities;
]>
<section id="introduction">
@ -235,8 +240,8 @@ this device driver, however, runs in kernel space, and the user
application in user space. So, the operating system provides an
interface between both. In Linux or Unix, these interfaces are in the
form of <quote>files</quote>
in the <filename class=directory>/dev</filename> directory (2.2.x kernels or
earlier) or <filename class=directory>/devfs</filename> directory
in the <filename class="directory">/dev</filename> directory (2.2.x kernels or
earlier) or <filename class="directory">/devfs</filename> directory
(2.4.x kernels and later). Each device supported in the kernel has a
representative as such a user space device file, and its functionality can
be accessed by classical Unix file I/O:
@ -248,10 +253,10 @@ representative as such a user space device file, and its functionality can
<listitem>
<para>
<emphasis role="strong"><filename class=directory>/proc</filename> interface.</emphasis>
<emphasis role="strong"><filename class="directory">/proc</filename> interface.</emphasis>
Linux (and some other UNIX operating systems) offer a file-like
interface to attached devices (and other OS-related information) via
the <filename class=directory>/proc</filename> directories. These
the <filename class="directory">/proc</filename> directories. These
<quote>files</quote> do not really exist, but it gives a familiar
interface to users, with which they can inspect the current status of
each device.
@ -411,7 +416,7 @@ Acquisition terminology
<para>
This Section introduces the terminology that this document uses when
talking about <quote>acquisitions.</quote> <xref linkend="fig-acq-seq">
talking about <quote>acquisitions.</quote> <xref linkend="fig-acq-seq"/>
depicts a typical acquisition <emphasis role="strong">sequence</emphasis>:
<itemizedlist>
@ -426,7 +431,7 @@ and the hardware need some finite
<listitem>
<para>
<anchor id="scan">
<anchor id="scan"/>
The sequence consists of a number of identically repeated
<emphasis role="strong">scans</emphasis>. This is where the actual
data acquisitions are taking place: data is read from the card, or
@ -448,14 +453,14 @@ on the minimum time needed to complete a full scan.
<listitem>
<para>
Each scan contains one or more
<anchor id="conversion">
<anchor id="conversion"/>
<emphasis role="strong">conversions</emphasis> on particular channels,
i.e., the AD/DA converter is activated on each of the programmed
channels, and produces a sample, again in a finite
<emphasis role="strong">conversion time</emphasis>, starting from the
moment in time called the
<emphasis role="strong">sample time</emphasis>
in <xref linkend="fig-acq-seq">
in <xref linkend="fig-acq-seq"/>
(sometimes also called the <quote>timestamp</quote>),
and caused by a
triggering event, called <emphasis role="strong">convert</emphasis>.
@ -493,7 +498,7 @@ scan.
</title>
<mediaobject>
<imageobject>
<imagedata fileref="acq-seq.gif" format="GIF">
<imagedata fileref="acq-seq.gif" format="GIF"/>
</imageobject>
<!--
<imageobject>
@ -695,10 +700,10 @@ structures.
Finally, &comedi; offers the previously mentioned
<quote>high-level</quote> interaction, i.e., at the level of user space
device drivers, through file operations on entries in the
<filename class=directory>/dev</filename> directory (for access to the
<filename class="directory">/dev</filename> directory (for access to the
device's functionality), or interactively from the command line
through the <quote>files</quote> in the
<filename class=directory>/proc</filename> directory (which allow to
<filename class="directory">/proc</filename> directory (which allow to
inspect the status of a &comedi; device).
</para>

View file

@ -7,12 +7,18 @@ $header="#include &lt;comedilib.h&gt;";
$end = "";
print
"<!--This file is autogenerated. Do not edit-->
<section>
'<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE article PUBLIC "-//OASIS//DTD DocBook XML V4.4//EN"
"http://www.oasis-open.org/docbook/xml/4.4/docbookx.dtd" [
<!ENTITY % comedilib_entities SYSTEM "comedilib.ent">
%comedilib_entities;
]>
<!--This file is autogenerated. Do not edit-->
<section id="lowleveldrivers">
<title>
Low-level drivers
Kernel Drivers
</title>
";
';
while(<>){
push @lines,$_;
@ -63,7 +69,8 @@ while($s = shift @lines){
$author =~ s/@/&#64;/g;
$author =~ s/</&lt;/g;
$author =~ s/>/&gt;/g;
print
$description =~ s/&/&amp;/g;
print
"
<section>
<title>

View file

@ -8,8 +8,15 @@ $end = "";
$refentry_end = "";
print
"<!--This file is autogenerated. Do not edit-->
";
'<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE article PUBLIC "-//OASIS//DTD DocBook XML V4.4//EN"
"http://www.oasis-open.org/docbook/xml/4.4/docbookx.dtd" [
<!ENTITY % comedilib_entities SYSTEM "comedilib.ent">
%comedilib_entities;
]>
<!--This file is autogenerated. Do not edit-->
<section>
';
while($s = <>){
chomp $s;
@ -110,6 +117,7 @@ while($s = <>){
print $end;
print $refentry_end;
print "</section>";
exit(0);

View file

@ -1,5 +1,9 @@
<!-- <!DOCTYPE section PUBLIC "-//OASIS//DTD DocBook V4.3//EN"> -->
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE article PUBLIC "-//OASIS//DTD DocBook XML V4.4//EN"
"http://www.oasis-open.org/docbook/xml/4.4/docbookx.dtd" [
<!ENTITY % comedilib_entities SYSTEM "comedilib.ent">
%comedilib_entities;
]>
<section id="acquisitionfunctions">
<title>
@ -11,7 +15,7 @@ This Section gives an overview of all &comedi; functions with which
application programmers can implement their data acquisition. (With
<quote>acquisition</quote> we mean all possible kinds of interfacing
with the cards: input, output, configuration, streaming, etc.)
<xref linkend="comedireference"> explains the function calls in full
<xref linkend="comedireference"/> explains the function calls in full
detail.
</para>
@ -57,13 +61,13 @@ the functions
int <link linkend="func-ref-comedi-dio-read">comedi_dio_read</link>(device,subdevice,channel,unsigned int *bit);
int <link linkend="func-ref-comedi-dio-write">comedi_dio_write</link>(device,subdevice,channel,unsigned int bit);
</programlisting>
The <parameter class=function>device</parameter> parameter is a
The <parameter class="function">device</parameter> parameter is a
<link linkend="ref-type-comedi-t">pointer</link>
to a successfully opened &comedi; device.
The <parameter class=function>subdevice</parameter> and
<parameter class=function>channel</parameter> parameters are positive
The <parameter class="function">subdevice</parameter> and
<parameter class="function">channel</parameter> parameters are positive
integers that indicate which subdevice and channel is used in the
acquisition. The integer <parameter class=function>bit</parameter>
acquisition. The integer <parameter class="function">bit</parameter>
contains the value of the acquired bit.
</para>
<para>
@ -72,7 +76,7 @@ the function
<programlisting>
<link linkend="func-ref-comedi-dio-config">comedi_dio_config</link>(device,subdevice,channel,unsigned int dir);
</programlisting>
The parameter <parameter class=function>dir</parameter> should be
The parameter <parameter class="function">dir</parameter> should be
either <literal>COMEDI_INPUT</literal> or
<literal>COMEDI_OUTPUT</literal>.
Many digital I/O subdevices group channels into blocks for
@ -87,15 +91,15 @@ function
<link linkend="func-ref-comedi-dio-bitfield">comedi_dio_bitfield</link>(device,subdevice,unsigned int write_mask,unsigned int *bits);
</programlisting>
Each channel is assigned to a bit in the
<parameter class=function>write_mask</parameter> and
<parameter class=function>bits</parameter>
<parameter class="function">write_mask</parameter> and
<parameter class="function">bits</parameter>
bitfield. If a bit in
<parameter class=function>write_mask</parameter> is set, the
corresponding bit in <parameter class=function>*bits</parameter> will
<parameter class="function">write_mask</parameter> is set, the
corresponding bit in <parameter class="function">*bits</parameter> will
be written to the corresponding digital output line.
Each digital line is then read and placed into
<parameter class=function>*bits</parameter>. The value
of bits in <parameter class=function>*bits</parameter> corresponding
<parameter class="function">*bits</parameter>. The value
of bits in <parameter class="function">*bits</parameter> corresponding
to digital output lines is undefined and device-specific. Channel
<literal>0</literal> is the least significant bit in the bitfield;
channel <literal>31</literal> is the most significant bit. Channels
@ -187,7 +191,7 @@ that can read more than one sample:
int <link linkend="func-ref-comedi-dio-read">comedi_data_read_n</link>(<link linkend="ref-type-comedi-t">comedi_t</link> *it, unsigned int subdev, unsigned int chan, unsigned int range,
unsigned int aref, <link linkend="ref-type-lsampl-t">lsampl_t</link> *data, unsigned int n)
</programlisting>
The number of samples, <parameter class=function>n</parameter>, is
The number of samples, <parameter class="function">n</parameter>, is
limited by the &comedi; implementation (to a maximum of 100 samples),
because the call is blocking.
</para>
@ -219,7 +223,7 @@ execute a multiple of identical acquisitions on the same channel, but
also to perform a
<link linkend="instructionsconfiguration">configuration</link> of a
channel.
<anchor id="anchor.instruction.list">
<anchor id="anchor.instruction.list"/>
An <emphasis>instruction list</emphasis> is a list of instructions,
possibly on different channels. Both instructions and instructions
lists are executed <emphasis>synchronously</emphasis>, i.e., while
@ -241,13 +245,13 @@ All the information needed to execute an instruction is stored in the
<link linkend="ref-type-comedi-insn">comedi_insn</link>
data structure:
<programlisting>
struct <anchor id="insn-data-structure">comedi_insn_struct{
<anchor id="insn-data-structure-insn">unsigned int insn; // integer encoding the type of acquisition
struct <anchor id="insn-data-structure"/>comedi_insn_struct{
<anchor id="insn-data-structure-insn"/>unsigned int insn; // integer encoding the type of acquisition
// (or configuration)
unsigned int n; // number of elements in data array
<link linkend="ref-type-lsampl-t">lsampl_t</link> <anchor id="insn-data-structure-data">*data; // pointer to data buffer
<link linkend="ref-type-lsampl-t">lsampl_t</link> <anchor id="insn-data-structure-data"/>*data; // pointer to data buffer
unsigned int subdev; // subdevice
unsigned int <anchor id="insn-data-structure-chanspec"><link linkend="ref-macro-CR-PACK">chanspec</link>; // encoded channel specification
unsigned int <anchor id="insn-data-structure-chanspec"/><link linkend="ref-macro-CR-PACK">chanspec</link>; // encoded channel specification
unsigned int unused[3];
} comedi_insn;
</programlisting>
@ -342,7 +346,7 @@ whole instruction (list) has finished.
Instructions for configuration
</title>
<para>
<xref linkend="instructions"> explains how instructions are used to do
<xref linkend="instructions"/> explains how instructions are used to do
<emphasis>acquisition</emphasis> on channels. This section explains
how they are used to <emphasis>configure</emphasis> a subdevice.
There are various sorts of configurations, and the
@ -485,7 +489,7 @@ Instruction for internal triggering
</title>
<para>
This special instruction has
<anchor id="insn-inttrig">INSN_INTTRIG as the
<anchor id="insn-inttrig"/>INSN_INTTRIG as the
<link linkend="insn-data-structure-insn">insn</link> flag in its
<link linkend="insn-data-structure">instruction data structure</link>.
Its execution causes an
@ -618,47 +622,47 @@ The command data structure
The command executes according to the information about the requested
acquisition, which is stored in the
<link linkend="ref-type-comedi-cmd">comedi_cmd</link>
<anchor id="command-data-struct">data structure:
<anchor id="command-data-struct"/>data structure:
<programlisting>
typedef struct comedi_cmd_struct comedi_cmd;
struct comedi_cmd_struct{
unsigned int subdev; // which subdevice to sample
unsigned int <anchor id="command-data-struct-flags">flags; // encode some configuration possibilities
unsigned int <anchor id="command-data-struct-flags"/>flags; // encode some configuration possibilities
// of the command execution; e.g.,
// whether a callback routine is to be
// called at the end of the command
unsigned int <anchor id="command-data-struct-start-src">start_src; // event to make the acquisition start
unsigned int <anchor id="command-data-struct-start-arg">start_arg; // parameters that influence this start
unsigned int <anchor id="command-data-struct-start-src"/>start_src; // event to make the acquisition start
unsigned int <anchor id="command-data-struct-start-arg"/>start_arg; // parameters that influence this start
unsigned int <anchor id="command-data-struct-scan-begin-src">scan_begin_src; // event to make a particular scan start
unsigned int <anchor id="command-data-struct-scan-begin-arg">scan_begin_arg; // parameters that influence this start`
unsigned int <anchor id="command-data-struct-scan-begin-src"/>scan_begin_src; // event to make a particular scan start
unsigned int <anchor id="command-data-struct-scan-begin-arg"/>scan_begin_arg; // parameters that influence this start`
unsigned int <anchor id="command-data-struct-convert-src">convert_src; // event to make a particular conversion start
unsigned int <anchor id="command-data-struct-convert-arg">convert_arg; // parameters that influence this start
unsigned int <anchor id="command-data-struct-convert-src"/>convert_src; // event to make a particular conversion start
unsigned int <anchor id="command-data-struct-convert-arg"/>convert_arg; // parameters that influence this start
unsigned int <anchor id="command-data-struct-scan-end-src">scan_end_src; // event to make a particular scan terminate
unsigned int <anchor id="command-data-struct-scan-end-arg">scan_end_arg; // parameters that influence this termination
unsigned int <anchor id="command-data-struct-scan-end-src"/>scan_end_src; // event to make a particular scan terminate
unsigned int <anchor id="command-data-struct-scan-end-arg"/>scan_end_arg; // parameters that influence this termination
unsigned int <anchor id="command-data-struct-stop-src">stop_src; // what make the acquisition terminate
unsigned int <anchor id="command-data-struct-stop-arg">stop_arg; // parameters that influence this termination
unsigned int <anchor id="command-data-struct-stop-src"/>stop_src; // what make the acquisition terminate
unsigned int <anchor id="command-data-struct-stop-arg"/>stop_arg; // parameters that influence this termination
unsigned int <anchor id="command-data-struct-chanlist">*chanlist; // pointer to list of channels to be sampled
unsigned int <anchor id="command-data-struct-chanlist-len">chanlist_len; // number of channels to be sampled
unsigned int <anchor id="command-data-struct-chanlist"/>*chanlist; // pointer to list of channels to be sampled
unsigned int <anchor id="command-data-struct-chanlist-len"/>chanlist_len; // number of channels to be sampled
sampl_t *<anchor id="command-data-struct-data">data; // address of buffer
unsigned int <anchor id="command-data-struct-data-len">data_len; // number of samples to acquire
sampl_t *<anchor id="command-data-struct-data"/>data; // address of buffer
unsigned int <anchor id="command-data-struct-data-len"/>data_len; // number of samples to acquire
};
</programlisting>
The start and end of the whole command acquisition sequence, and the
start and end of each scan and of each conversion, is triggered by a
so-called <emphasis>event</emphasis>. More on these in
<xref linkend="comedicmdsources">.
<xref linkend="comedicmdsources"/>.
</para>
<para>
The <parameter class=function>subdev</parameter> member of the
The <parameter class="function">subdev</parameter> member of the
<link linkend="ref-type-comedi-cmd">comedi_cmd</link> structure is
the index of the subdevice the command is intended for. The
<link linkend="func-ref-comedi-find-subdevice-by-type">comedi_find_subdevice_by_type()</link>
@ -681,7 +685,7 @@ that should be stepped through for each scan. The elements of the
<link linkend="command-data-struct-chanlist">chanlist</link> array should be
initialized by <quote>packing</quote> the channel, range and reference
information together with the
<parameter class=function>
<parameter class="function">
<link linkend="ref-macro-CR-PACK">CR_PACK()</link>
</parameter>
macro.
@ -712,7 +716,7 @@ these bits are explained in a
<section id="comedicmdsources">
<title>
The command trigger events
<anchor id="source.trigger.anchor">
<anchor id="source.trigger.anchor"/>
</title>
<para>
A command is a very versatile acquisition instruction, in the sense
@ -726,10 +730,10 @@ start a <link linkend="scan">scan</link>, start a
<link linkend="conversion">conversion</link>, stop a scan, and stop
the acquisition. Each event can be given its own
<emphasis><link linkend="source.trigger.anchor">source</link></emphasis>
(the <parameter class=function>*_src</parameter> members in the
(the <parameter class="function">*_src</parameter> members in the
<link linkend="ref-type-comedi-cmd">comedi_cmd</link> data
structure). And each event source can have a corresponding
argument (the <parameter class=function>*_arg</parameter> members of
argument (the <parameter class="function">*_arg</parameter> members of
the <link linkend="ref-type-comedi-cmd">comedi_cmd</link> data
structure) whose meaning depends on the type of source trigger.
For example, to specify an external digital line <quote>3</quote> as a
@ -740,8 +744,8 @@ sources), you would use
</para>
<para>
The following paragraphs discuss in somewhat more detail the trigger
event sources(<parameter class=function>*_src</parameter>), and the
corresponding arguments (<parameter class=function>*_arg</parameter>).
event sources(<parameter class="function">*_src</parameter>), and the
corresponding arguments (<parameter class="function">*_arg</parameter>).
</para>
<para>
The start of an acquisition is controlled by the
@ -751,7 +755,7 @@ The available options are:
<listitem>
<para>
<anchor id="trig-now-start-src">
<anchor id="trig-now-start-src"/>
TRIG_NOW: the
<link linkend="command-data-struct-start-src">start_src</link>
event occurs
@ -766,7 +770,7 @@ supported.
<listitem>
<para>
<anchor id="trig-follow-start-src">
<anchor id="trig-follow-start-src"/>
TRIG_FOLLOW: (For an output device.) The
<link linkend="command-data-struct-start-src">start_src</link>
event occurs when data is written to the buffer.
@ -775,7 +779,7 @@ event occurs when data is written to the buffer.
<listitem>
<para>
<anchor id="trig-ext-start-src">
<anchor id="trig-ext-start-src"/>
TRIG_EXT: the start event occurs when an external trigger signal
occurs; e.g., a rising edge of a digital line.
<link linkend="command-data-struct-start-arg">start_arg</link>
@ -785,7 +789,7 @@ chooses the particular digital line.
<listitem>
<para>
<anchor id="trig-int-start-src">
<anchor id="trig-int-start-src"/>
TRIG_INT: the start event occurs on a &comedi; internal signal, which
is typically caused by an
<link linkend="insn-inttrig">INSN_INTTRIG instruction</link>.
@ -801,7 +805,7 @@ The available options are:
<listitem>
<para>
<anchor id="trig-timer-start-scan">
<anchor id="trig-timer-start-scan"/>
TRIG_TIMER:
<link linkend="command-data-struct-scan-begin-src">scan_begin</link>
events occur periodically. The time between
@ -814,7 +818,7 @@ nanoseconds.
<listitem>
<para>
<anchor id="trig-follow-start-scan">
<anchor id="trig-follow-start-scan"/>
TRIG_FOLLOW: The
<link linkend="command-data-struct-scan-begin-src">scan_begin</link>
event occurs immediately after a
@ -825,7 +829,7 @@ event occurs.
<listitem>
<para>
<anchor id="trig-ext-start-scan">
<anchor id="trig-ext-start-scan"/>
TRIG_EXT: the
<link linkend="command-data-struct-scan-begin-src">scan_begin</link>
event occurs when an external trigger signal
@ -851,8 +855,8 @@ fields:
<listitem>
<para>
<anchor id="convert-trig-timer">
<anchor id="trig-timer">
<anchor id="convert-trig-timer"/>
<anchor id="trig-timer"/>
TRIG_TIMER: the conversion events occur periodically. The time
between convert events is
<link linkend="command-data-struct-convert-arg">convert_arg</link>
@ -862,8 +866,8 @@ nanoseconds.
<listitem>
<para>
<anchor id="convert-trig-ext">
<anchor id="trig-ext">
<anchor id="convert-trig-ext"/>
<anchor id="trig-ext"/>
TRIG_EXT: the conversion events occur when an external trigger signal
occurs, e.g., a rising edge of a digital line.
<link linkend="command-data-struct-convert-arg">convert_arg</link>
@ -873,8 +877,8 @@ chooses the particular digital line.
<listitem>
<para>
<anchor id="convert-trig-now">
<anchor id="trig-now">
<anchor id="convert-trig-now"/>
<anchor id="trig-now"/>
TRIG_NOW: All conversion events in a
<link linkend="scan">scan</link> occur simultaneously.
</para>
@ -899,8 +903,8 @@ and <link linkend="command-data-struct-stop-arg">stop_arg</link>:
<listitem>
<para>
<anchor id="acquisition-end-trig-count">
<anchor id="trig-count">
<anchor id="acquisition-end-trig-count"/>
<anchor id="trig-count"/>
TRIG_COUNT: stop the acquisition after
<link linkend="command-data-struct-stop-arg">stop_arg</link>
scans.
@ -909,8 +913,8 @@ scans.
<listitem>
<para>
<anchor id="acquisition-end-trig-none">
<anchor id="trig-none">
<anchor id="acquisition-end-trig-none"/>
<anchor id="trig-none"/>
TRIG_NONE: perform continuous acquisition, until stopped using
<link linkend="func-ref-comedi-cancel">comedi_cancel()</link>.
</para>
@ -928,7 +932,7 @@ There are a couple of less usual or not yet implemented events:
<listitem>
<para>
<anchor id="trig-time">
<anchor id="trig-time"/>
TRIG_TIME:
cause an event to occur at a particular time.
</para>
@ -939,7 +943,7 @@ cause an event to occur at a particular time.
<listitem>
<para>
<anchor id="trigother-event">
<anchor id="trigother-event"/>
TRIG_OTHER: driver specific event trigger.
</para>
<para>
@ -971,7 +975,7 @@ supports.
<section id="comedicmdflags">
<title>
The command flags
<anchor id="source.flags.anchor">
<anchor id="source.flags.anchor"/>
</title>
<para>
@ -985,7 +989,7 @@ The meaning of the field is as follows:
<listitem>
<para>
<anchor id="trig-rt">
<anchor id="trig-rt"/>
TRIG_RT: ask the driver to use a
<emphasis role="strong">hard real-time</emphasis> interrupt handler.
This will reduce latency in handling interrupts from your data
@ -1001,7 +1005,7 @@ nothing.
<listitem>
<para>
<anchor id="trig-wake-eos">
<anchor id="trig-wake-eos"/>
TRIG_WAKE_EOS:
where <quote>EOS</quote> stands for <quote>End of Scan</quote>. Some
drivers will change their behaviour when this flag is set, trying to
@ -1015,7 +1019,7 @@ frequent event than the filling up of the data buffer.
<listitem>
<para>
<anchor id="trig-round-nearest">
<anchor id="trig-round-nearest"/>
TRIG_ROUND_NEAREST:
round to nearest supported timing period, the default.
This flag (as well as the following three), indicates how timing
@ -1026,21 +1030,21 @@ timing requested.
<listitem>
<para>
<anchor id="trig-round-down">
<anchor id="trig-round-down"/>
TRIG_ROUND_DOWN: round period down.
</para>
</listitem>
<listitem>
<para>
<anchor id="trig-round-up">
<anchor id="trig-round-up"/>
TRIG_ROUND_UP: round period up.
</para>
</listitem>
<listitem>
<para>
<anchor id="trig-round-up-next">
<anchor id="trig-round-up-next"/>
TRIG_ROUND_UP_NEXT:
this one doesn't do anything, and I don't know what it was intended
to do&hellip;?
@ -1049,7 +1053,7 @@ to do&hellip;?
<listitem>
<para>
<anchor id="trig-dither">
<anchor id="trig-dither"/>
TRIG_DITHER: enable dithering? Dithering is a software technique to
smooth the influence of discretization <quote>noise</quote>.
</para>
@ -1057,7 +1061,7 @@ smooth the influence of discretization <quote>noise</quote>.
<listitem>
<para>
<anchor id="trig-deglitch">
<anchor id="trig-deglitch"/>
TRIG_DEGLITCH: enable deglitching? Another <quote>noise</quote>
smoothing technique.
</para>
@ -1065,7 +1069,7 @@ smoothing technique.
<listitem>
<para>
<anchor id="trig-write">
<anchor id="trig-write"/>
TRIG_WRITE:
write to bidirectional devices. Could be useful, in principle, if
someone wrote a driver that supported commands for a digital I/O
@ -1075,14 +1079,14 @@ device that could do either input or output.
<listitem>
<para>
<anchor id="trig-bogus">
<anchor id="trig-bogus"/>
TRIG_BOGUS: do the motions?
</para>
</listitem>
<listitem>
<para>
<anchor id="trig-other">
<anchor id="trig-other"/>
TRIG_CONFIG: perform configuration, not triggering. This is a legacy
of the deprecated
<link linkend="ref-type-comedi-cmd">comedi_trig_struct</link>

View file

@ -1,4 +1,14 @@
<!-- <!DOCTYPE article PUBLIC "-//OASIS//DTD DocBook V4.2//EN" -->
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE article PUBLIC "-//OASIS//DTD DocBook XML V4.4//EN"
"http://www.oasis-open.org/docbook/xml/4.4/docbookx.dtd" [
<!ENTITY % comedilib_entities SYSTEM "comedilib.ent">
%comedilib_entities;
]>
<section id="comedireference" xmlns:xi="http://www.w3.org/2001/XInclude">
<title>
&comedi; Reference
</title>
<section id="comedi-comedilib-h">
<title>
@ -59,7 +69,7 @@ The <parameter>aref</parameter> argument indicates what reference you
want the device to use. It can be any of the following:
<variablelist>
<varlistentry>
<term>AREF_GROUND <anchor id="aref-ground"> </term>
<term>AREF_GROUND <anchor id="aref-ground"/> </term>
<listitem>
<para>
is for inputs/outputs referenced to ground.
@ -67,7 +77,7 @@ want the device to use. It can be any of the following:
</listitem>
</varlistentry>
<varlistentry>
<term>AREF_COMMON <anchor id="aref-common"> </term>
<term>AREF_COMMON <anchor id="aref-common"/> </term>
<listitem>
<para>
is for a <quote>common</quote> reference (the low inputs of all the
@ -76,7 +86,7 @@ channels are tied together, but are isolated from ground).
</listitem>
</varlistentry>
<varlistentry>
<term>AREF_DIFF <anchor id="aref-diff"> </term>
<term>AREF_DIFF <anchor id="aref-diff"/> </term>
<listitem>
<para>
is for differential inputs/outputs.
@ -84,7 +94,7 @@ channels are tied together, but are isolated from ground).
</listitem>
</varlistentry>
<varlistentry>
<term>AREF_OTHER <anchor id="aref-other"> </term>
<term>AREF_OTHER <anchor id="aref-other"/> </term>
<listitem>
<para>
is for any reference that does not fit into the above categories.
@ -180,7 +190,7 @@ information about a subdevice. This structure is usually filled in
automatically when the driver is loaded (<quote>attached</quote>), so
programmers need not access this data structure directly.
<programlisting>
typedef struct subdevice_struct <anchor id="ref-type-subdevice">subdevice;
typedef struct subdevice_struct <anchor id="ref-type-subdevice"/>subdevice;
struct subdevice_struct{
unsigned int type;
@ -469,7 +479,7 @@ to the driver. Valid instruction types are:
<variablelist>
<varlistentry>
<term>
<anchor id="insn-read">
<anchor id="insn-read"/>
INSN_READ
</term>
<listitem>
@ -480,7 +490,7 @@ read values from an input channel
</varlistentry>
<varlistentry>
<term>
<anchor id="insn-write">
<anchor id="insn-write"/>
INSN_WRITE
</term>
<listitem>
@ -491,7 +501,7 @@ write values to an output channel
</varlistentry>
<varlistentry>
<term>
<anchor id="insn-bits">
<anchor id="insn-bits"/>
INSN_BITS
</term>
<listitem>
@ -502,7 +512,7 @@ read/write values on multiple digital I/O channels
</varlistentry>
<varlistentry>
<term>
<anchor id="insn-config">
<anchor id="insn-config"/>
INSN_CONFIG
</term>
<listitem>
@ -513,7 +523,7 @@ configure a subdevice
</varlistentry>
<varlistentry>
<term>
<anchor id="insn-gtod">
<anchor id="insn-gtod"/>
INSN_GTOD
</term>
<listitem>
@ -525,7 +535,7 @@ and microseconds values are of type <link linkend="ref-type-lsampl-t">lsampl_t</
</varlistentry>
<varlistentry>
<term>
<anchor id="insn-wait">
<anchor id="insn-wait"/>
INSN_WAIT
</term>
<listitem>
@ -629,4 +639,37 @@ a list of instructions.
</section>
</section>
<section id="functionreference">
<title>Functions</title>
<section>
<title>Core</title>
<xi:include href="funcref.xml"/>
</section>
<section>
<title>Asyncronous Commands</title>
<xi:include href="command_funcref.xml"/>
</section>
<section>
<title>Calibration</title>
<xi:include href="calibration_funcref.xml"/>
</section>
<section>
<title>Digital I/O</title>
<xi:include href="dio_funcref.xml"/>
</section>
<section>
<title>Error Reporting</title>
<xi:include href="error_funcref.xml"/>
</section>
<section>
<title>Extensions</title>
<xi:include href="extensions_funcref.xml"/>
</section>
<section>
<title>Deprecated</title>
<xi:include href="deprecated_funcref.xml"/>
</section>
</section>
</section>

View file

@ -1,4 +1,9 @@
<!-- <!DOCTYPE article PUBLIC "-//OASIS//DTD DocBook V4.2//EN" "docbook/dtd/4.2/docbook.dtd"> -->
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE article PUBLIC "-//OASIS//DTD DocBook XML V4.4//EN"
"http://www.oasis-open.org/docbook/xml/4.4/docbookx.dtd" [
<!ENTITY % comedilib_entities SYSTEM "comedilib.ent">
%comedilib_entities;
]>
<section id="writingprograms">
<title>
@ -8,13 +13,13 @@ Writing &comedi; programs
This Section describes how a well-installed and configured &comedi;
package can be used in an application, to communicate data with a set
of &comedi; devices.
<xref linkend="acquisitionfunctions"> gives more details about
<xref linkend="acquisitionfunctions"/> gives more details about
the various acquisition functions with which the application
programmer can perform data acquisition in &comedi;.
</para>
<para>
Also don't forget to take a good look at the
<filename class=directory>demo</filename>
<filename class="directory">demo</filename>
directory of the Comedilib source code. It contains lots of examples
for the basic functionalities of &comedi;.
</para>
@ -43,7 +48,7 @@ int main(int argc,char *argv[])
it=<link linkend="func-ref-comedi-open">comedi_open</link>("/dev/comedi0");
<link linkend="func-ref-comedi-data-read">comedi_data_read</link>(it,subdev,chan,range,aref, & data);
<link linkend="func-ref-comedi-data-read">comedi_data_read</link>(it,subdev,chan,range,aref, &amp;data);
printf("%d\n",data);
@ -55,7 +60,7 @@ The
<link linkend="func-ref-comedi-open">comedi_open()</link>
</function> can only be successful if the
<filename>comedi0</filename> device file is configured to point to a
valid &comedi; driver. <xref linkend="cardconfiguration"> explains
valid &comedi; driver. <xref linkend="cardconfiguration"/> explains
how this driver is linked to the <quote>device file</quote>.
</para>
<para>
@ -72,11 +77,11 @@ cc tut1.c -lcomedi -o tut1
</para>
<para>
The <parameter class=function>range</parameter> variable tells
The <parameter class="function">range</parameter> variable tells
&comedi; which gain to use when measuring an analog voltage. Since we
don't know (yet) which numbers are valid, or what each means, we'll
use <literal>0</literal>, because it won't cause errors. Likewise
with <parameter class=function>aref</parameter>, which determines the
with <parameter class="function">aref</parameter>, which determines the
analog reference used.
</para>
</section>
@ -147,19 +152,19 @@ typedef struct{
unsigned int unit;
}comedi_range;
</programlisting>
The structure element <parameter class=function>min</parameter>
The structure element <parameter class="function">min</parameter>
represents the voltage corresponding to
<link linkend="func-ref-comedi-data-read">comedi_data_read()</link>
returning <literal>0</literal>,
and <parameter class=function>max</parameter> represents
and <parameter class="function">max</parameter> represents
<link linkend="func-ref-comedi-data-read">comedi_data_read()</link>
returning <parameter class=function>maxdata</parameter>,
returning <parameter class="function">maxdata</parameter>,
(i.e., <literal>4095</literal> for <literal>12</literal> bit A/C
converters, <literal>65535</literal> for <literal>16</literal> bit,
or, <literal>1</literal> for digital input; more on this in a bit.)
The <parameter class=function>unit</parameter> entry tells you if
<parameter class=function>min</parameter> and
<parameter class=function>max</parameter> refer to voltage, current,
The <parameter class="function">unit</parameter> entry tells you if
<parameter class="function">min</parameter> and
<parameter class="function">max</parameter> refer to voltage, current,
or are dimensionless (e.g., for digital I/O).
</para>
@ -206,7 +211,7 @@ file=<link linkend="func-ref-comedi-open">comedi_open</link>("/dev/comedi0");
</programlisting>
<para>
where <parameter class=function>file</parameter> is of type
where <parameter class="function">file</parameter> is of type
<parameter>(<link linkend="ref-type-comedi-t">comedi_t</link> *)</parameter>.
This function calls <function>open()</function>, as done explicitly in
a previous section, but also fills the
@ -216,7 +221,7 @@ structure with lots of goodies; this information will be useful soon.
<para>
Specifically, you need to know
<parameter class=function>maxdata</parameter> for a specific
<parameter class="function">maxdata</parameter> for a specific
subdevice/channel. How about:
<programlisting>
@ -451,13 +456,13 @@ void <link linkend="dds-output">dds_output</link>(sampl_t *buf,int n);
void <link linkend="dds-init">dds_init</link>(void);
/* This define determines which waveform to use. */
#define <anchor id="dds-init-function">dds_init_function <link linkend="dds-init-sine">dds_init_sine</link>
#define <anchor id="dds-init-function"/>dds_init_function <link linkend="dds-init-sine">dds_init_sine</link>
void <link linkend="dds-init-sine">dds_init_sine</link>(void);
void <link linkend="dds-init-pseudocycloid">dds_init_pseudocycloid</link>(void);
void <link linkend="dds-init-sawtooth">dds_init_sawtooth</link>(void);
int <anchor id="comedi-internal-trigger">comedi_internal_trigger(<link linkend="ref-type-comedi-t">comedi_t</link> *dev, unsigned int subd, unsigned int trignum)
int <anchor id="comedi-internal-trigger"/>comedi_internal_trigger(<link linkend="ref-type-comedi-t">comedi_t</link> *dev, unsigned int subd, unsigned int trignum)
{
<link linkend="ref-type-comedi-insn">comedi_insn</link> insn;
<link linkend="ref-type-lsampl-t">lsampl_t</link> data[1];
@ -532,24 +537,22 @@ int main(int argc, char *argv[])
<link linkend="dds-output">dds_output</link>(data,BUF_LEN);
<link linkend="dds-output">dds_output</link>(data,BUF_LEN);
dump_cmd(stdout,<![CDATA[&cmd]]>);
dump_cmd(stdout,&amp;cmd);
if ((err = <link linkend="func-ref-comedi-command">comedi_command</link>(dev, <![CDATA[&cmd]]>)) < 0) {
if ((err = <link linkend="func-ref-comedi-command">comedi_command</link>(dev, &amp;cmd)) &lt; 0) {
<link linkend="func-ref-comedi-perror">comedi_perror</link>("comedi_command");
exit(1);
}
m=write(comedi_fileno(dev),data,BUF_LEN*sizeof(sampl_t));
if(<![CDATA[m<0]]>){
if(m &lt; 0){
perror("write");
exit(1);
}
printf("m=%d\n",m);
ret = <link linkend="comedi-internal-trigger">comedi_internal_trigger</link>(dev, subdevice, 0);
<![CDATA[
if(ret<0){
]]>
if(ret &lt; 0){
perror("comedi_internal_trigger\n");
exit(1);
}
@ -559,9 +562,7 @@ int main(int argc, char *argv[])
n=BUF_LEN*sizeof(sampl_t);
while(n>0){
m=write(comedi_fileno(dev),(void *)data+(BUF_LEN*sizeof(sampl_t)-n),n);
<![CDATA[
if(m<0){
]]>
if(m &lt; 0){
perror("write");
exit(0);
}
@ -575,17 +576,15 @@ int main(int argc, char *argv[])
}
#define WAVEFORM_SHIFT 16
<![CDATA[
#define WAVEFORM_LEN (1<<WAVEFORM_SHIFT)
]]>
#define WAVEFORM_MASK (WAVEFORM_LEN-1)
#define WAVEFORM_LEN (1 &lt;&lt; WAVEFORM_SHIFT)
#define WAVEFORM_MASK (WAVEFORM_LEN - 1)
sampl_t waveform[WAVEFORM_LEN];
unsigned int acc;
unsigned int adder;
void <anchor id="dds-init">dds_init(void)
void <anchor id="dds-init"/>dds_init(void)
{
<![CDATA[
adder=waveform_frequency/freq*(1<<16)*(1<<WAVEFORM_SHIFT);
@ -594,7 +593,7 @@ void <anchor id="dds-init">dds_init(void)
<link linkend="dds-init-function">dds_init_function</link>();
}
void <anchor id="dds-output">dds_output(sampl_t *buf,int n)
void <anchor id="dds-output"/>dds_output(sampl_t *buf,int n)
{
int i;
sampl_t *p=buf;
@ -609,7 +608,7 @@ void <anchor id="dds-output">dds_output(sampl_t *buf,int n)
}
void <anchor id="dds-init-sine">dds_init_sine(void)
void <anchor id="dds-init-sine"/>dds_init_sine(void)
{
int i;
@ -621,7 +620,7 @@ void <anchor id="dds-init-sine">dds_init_sine(void)
}
/* Yes, I know this is not the proper equation for a cycloid. Fix it. */
void <anchor id="dds-init-pseudocycloid">dds_init_pseudocycloid(void)
void <anchor id="dds-init-pseudocycloid"/>dds_init_pseudocycloid(void)
{
int i;
double t;
@ -638,7 +637,7 @@ void <anchor id="dds-init-pseudocycloid">dds_init_pseudocycloid(void)
]]>
}
void <anchor id="dds-init-sawtooth">dds_init_sawtooth(void)
void <anchor id="dds-init-sawtooth"/>dds_init_sawtooth(void)
{
int i;