Functions.rst 44.8 KB
Newer Older
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
=========
Functions
=========

.. index:: Functions

This part describes the Functions that are defined in the simple
CAN-interface.

Note that all functions that according to the following description print to
the console actually use the `dbg` module to print. `dbg` is part of the tool
library which is part of MultiCAN. `dbg` allows to redirect the output to a
file or a simple network server, for further details see `dbg` documentation.

.. index::
   single: sci_open

sci_open
--------

::

  sci_Return sci_open(sci_Struc **s_struc, char *app_name,
                      sci_Errcode *err);

This is the open-function for the SCI-library. A process or thread can only
use the other functions of the library, when it has once called
`sci_open`.

Parameters and return-codes:

`s_struc`
  This is the pointer to the created sci-structure. The calling
  program gets a pointer to a new created internal sci-structure. The user
  program should not read or write to that structure. Since the internal details
  of this structure are hidden and it's size is unknown to user, the user
  program should not define variables of the type `sci_Struc` but only
  a *pointer* to a variable of this type.

`app_name`
  This parameter may be an empty string or a string that
  identifies the application. In case of an empty-string a new sci-structure
  is created that is unique for that process (note: not unique for the
  *thread*). If the string is not empty, it is stored in the SCI-library.
  Any program that opens the library with the same string gets the same
  sci-structure.

`err`
  This is the only function in sci, where the error-code is
  returned directly and has not to be requested with `sci_get_errcode`.
  The user program should have a variable of the type `sci_Errcode`
  defined and provide a pointer to that variable with the parameter
  `err`.

return value
  This function returns either `SCI_NOTHING` in case of
  successful execution or `SCI_ERROR` in case of an error. The error-
  code can then be found the user's error-variable, provided by the
  `err` parameter.

.. index::
   single: sci_close

sci_close
---------

::

  sci_Return sci_close(sci_Struc **s_struc);
  

This function is used (by a thread) to close the SCI-library. All CAN objects
that were previously defined (by that thread) and the sci-structure,
are deleted.

Parameters and return-codes:

`s_struc`
  This is the address of a pointer that points to the
  sci-structure. After successful closing, the internal sci-structure is deleted
  and the given pointer is changed to a `NULL` pointer.

return value
  This function returns `SCI_NOTHING` on success,
  `SCI_ERROR` in case of an error. In case of an error, the
  sci-structure remains defined and the pointer to that structure remains
  valid.

.. index::
   single: sci_init

sci_init
--------

::

  sci_Return sci_init(sci_Struc *s_struc,
                      unsigned short port, sci_Bitrate bitrate);
  
This function initializes a CAN-port with a certain bitrate. In some
implementations of sci, a CAN-port cannot be accessed before it has been
initialized once with `sci_init()`. In multitasking implementations
of sci, `SCI_AUTHORIZE_ERR` - error occurs when the current thread is
not the first thread that has used the SCI-library, see also the description
of `SCI_AUTHORIZE_ERR`, which is part of the `sci_Errcode`
enumeration type. Portable programs can call `sci_init` for each port
they use and just ignore a possible `SCI_AUTHORIZE_ERR` - error.

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`port`
  This is port that is to be initialized. It depends on your
  implementation of sci and on your installed CAN interface hardware how many
  ports are available. Valid port numbers must be greater or equal to zero.

`bitrate`
  This parameter specifies the bitrate for the port. Valid
  bitrates are defined in the `sci_Bitrate` data-type.

return value
  This function returns `SCI_NOTHING` in case of success or
  `SCI_ERROR` in case of an error.

.. index::
   single: sci_reset

sci_reset
---------

::

  sci_Return sci_reset(sci_Struc *s_struc, unsigned short port);
  
This function resets a CAN-port. It is similar in it's function to
`sci_init`, but the bitrate of the port remains unchanged. All
CAN-objects on this port are lost and have to be re-defined. Depending on the
underlaying hardware, it may be that it is not possible to reset single
CAN-ports independently. The VME-CAN2 card for example, has 2 CAN ports but
a card-reset resets both ports. In multitasking implementations of sci,
`SCI_AUTHORIZE_ERR` - error occurs when the current thread is not the
first thread that has used the SCI-library, see also the description of
`SCI_AUTHORIZE_ERR`, which is part of the `sci_Errcode`
enumeration type.

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`port`
  This is port that is to be initialized. It depends on your
  implementation of sci and on your installed CAN interface hardware how many
  ports are available. Valid port numbers must be greater or equal to zero.

return value
  This function returns `SCI_NOTHING` in case of success or
  `SCI_ERROR` in case of an error.

.. index::
   single: sci_get_bitrate

sci_get_bitrate
---------------

::

  sci_Return sci_get_bitrate(sci_Struc *s_struc,
                             unsigned short port, sci_Bitrate *bitrate);
  

This function returns the bitrate that was set for a specific port. The
port-parameter may be a real-port or a plug-port. The bitrate is returned
in the `bitrate` parameter.

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`port`
  This is port that is to be examined. This may also
  be a plug-port, in this case the bitrate of the corresponding real-port
  is returned.

`bitrate`
  The current bitrate is returned via this parameter. Note
  that the type of this variable is not `int` but `sci_Bitrate`.

return value
  This function returns `SCI_NOTHING` in case of success or
  `SCI_ERROR` in case of an error.

.. index::
   single: sci_get_errcode

sci_get_errcode
---------------

::

  sci_Return sci_get_errcode(sci_Struc *s_struc, sci_Errcode *errcode);
  
This function returns the last valid error-code for a thread. It is typically
called immediately after another sci-function returned the `SCI_ERROR`
flag. If another sci_function is called after the error but before
`sci_get_errcode()`, the original errorcode is lost.

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`errcode`
  This is a pointer to a variable of the type
  `sci_Errcode` that is defined in the user program. The current
  errorcode for the current thread is written to that user-variable.

return value
  This function always returns `SCI_NOTHING`.

.. index::
   single: sci_get_object

sci_get_object
--------------

::

  sci_Return sci_get_object(sci_Struc *s_struc, sci_Object **object,
                            unsigned short port, int id)

This function returns the `sci_Object` for a given port number and CAN object id.

Parameters and return-codes:

`s_struc`
  This is the address of a pointer that points to the
  sci-structure that was created by `sci_open`.

`object`
  This is the address of a pointer to an sci-object. After
  successful execution of this function the pointer points to the 
  sci_Object.

`port`
  This is the port-number of the CAN-object.

`id`
  This is the CAN-id of the object.

return value
  This function returns either `SCI_NOTHING` in case of
  successful execution or `SCI_ERROR` in case of an error.

.. index::
   single: sci_get_info

sci_get_info
------------

::

  sci_Return sci_get_info(sci_Struc *s_struc, sci_Object *object,
                          unsigned short *port, int *id, int *length, 
                          int *timeout, sci_Object_Type *type)
  
This function returns the properties of a sci-object. With this function it is
possible to get all properties of an object, that were specified with the call
of `sci_init_object`, back.

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`object`
  This is a pointer the sci-object that is to be examined.

`port`
  This is a pointer to an integer-variable of the user program. The
  port-number of the object is written to that variable.

`id`
  This is a pointer to an integer-variable of the user program. The
  CAN-id of the object is written to that variable.

`length`
  This is a pointer to an integer-variable of the user program.
  The length of the object is written to that variable.

`timeout`
  This is a pointer to an integer-variable of the user program.
  The timeout that was specified for that object is written to this variable.

`type`
  This is a pointer to a variable of the type
  `sci_Object_Type` that should be defined in the user program. The type
  of the sci-object is written to this variable.

return value
  This function always returns `SCI_NOTHING` on success and
  `SCI_ERROR` in case of an error (e.g. when `object` is
  a `NULL` pointer).

.. index::
   single: sci_get_timestamp

sci_get_timestamp
-----------------

::

  sci_Return sci_get_timestamp(sci_Struc *s_struc, sci_Object *object,
                               unsigned long long *pstamp, int *pvalid,
                               unsigned char *mode, unsigned char *irq_cnt)
  
This function returns the timestamp of an sci-write object. The timestamp
is set, when the write operation on the CAN bus actually takes place.
It is an integer of type long long (64 bits), where the value 0 defines
the time when the IOC was booted. Note that the timestamp may be invalid.
This is the case when a write operation is in progress but not
yet completed.

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`object`
  This is a pointer the sci-object that is to be examined.

`pstamp`
  This is a pointer to an integer-variable of type long long
  in the user program. The timestamp is is written to that variable.

`pvalid`
  This is a pointer to an integer-variable of the user program.
  If the timestamp is valid, a non-zero value is written to that variable.
  0 is written to that variable when the timestamp is invalid.

`mode`
  This is a pointer to an unsigned char variable. Here the function returns the
  internal timestamp mode of VCAN.

`irq_cnt`
  This is a pointer to an unsigned char variable. Here the function returns the
  internal VCAN interrupt counter of the CAN object.

returns
  This function always returns `SCI_NOTHING` on success and
  `SCI_ERROR` in case of an error.

.. index::
   single: sci_obj_dump_buf

sci_obj_dump_buf
----------------

::

  sci_Return sci_obj_dump_buf(char *buf,
                              sci_Struc *s_struc, sci_Object *object);

Prints information about the object to a string buffer. The information
includes the CAN-id, length, timeout, port and object type. The buffer `buf`
must have room for 80 characters.

Parameters and return-codes:

`buf`
The address of an array of characters, at least 80 characters long.

`s_struc`
  This is the sci-structure, created by `sci_open()`

`object`
  This is a pointer the sci-object that is to be examined.

.. index::
   single: sci_obj_dump

sci_obj_dump
------------

::

  sci_Return sci_obj_dump(sci_Struc *s_struc, sci_Object *object);

Prints information about the object to the console. The information
includes the CAN-id, length, timeout, port and object type. 

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`object`
  This is a pointer the sci-object that is to be examined.

.. index::
   single: sci_link_object

sci_link_object
---------------

::

  sci_Return sci_link_object(sci_Struc *s_struc,
                             unsigned short read_port , int read_id, 
                             unsigned short write_port, int write_id, 
                             int length, int timeout,
                             void *read_user, void *write_user)
  
This function defines a CAN link between two CAN ports on
a single CAN card. When a certain CAN object is received on the
first port, it is automatically written to the second port with
a (possibly) different CAN-ID. This uses a mechanism of the
VME-CAN2 or VME-CAN4 card which means the the VME CARDS perform
the forwarding operation without involving the VME CPU.
One measurement showed the forwarding took about 130 microseconds
with a jitter of just +-2 microseconds.

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`read_port`
  This is the port were the read CAN object is defined.

`read_id`
  This is CAN object ID of the read object.

`write_port`
  This is the port were the write CAN object is defined.

`length`
  This is the length of the CAN objects.

`timeout`
  This is the timeout parameter of the two CAN objects,
  but it has only a meaning for the write object.

`read_user`
  This is the optional user-part pointer of the read object.

`write_user`
  This is the optional user-part pointer of the write object.

returns
  This function always returns `SCI_NOTHING` on success and
  `SCI_ERROR` in case of an error.

.. index::
   single: sci_init_object

sci_init_object
---------------

::

  sci_Return sci_init_object(sci_Struc *s_struc, sci_Object **object,
                             unsigned short port, int id, int length, 
                             int timeout, sci_Object_Type type, void *userp)
  

This function initializes a single CAN-object. A sci-object structure is
created that is used by all other sci functions that work on single
CAN-objects. Note that each sci-object contains a user part that can be used
to store user-defined data for each object. See also the description of
the type `sci_Object`.

If there was already an sci_Object defined for that CAN-id,
`sci_init_object()` either returns an error if the object's properties
do not exactly match the already defined object, or it duplicates the
already existing object. A `SCI_EXISTS`-flag signals that an already
existing sci-object was found. For a description of duplicated objects see
also `sci_dup_object()`.

Note that the user-part of the `sci_Object` (see also description of this
data-type) is initialized with zero- bytes. Note too, that remote-write
objects are initialized with a number of zero-bytes that correspond to the
object's length and can be read by another CAN participant from that moment
on.

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`object`
  This is the address of a pointer to an sci-object. After
  successful execution of this function the pointer points to the new created
  sci_Object.

`port`
  This is the port-number of the CAN-object.

`id`
  This is the CAN-id of the object.

`length`
  This is a the length of the CAN-object. The object is defined
  with a certain length, that can range from 0 to 8 bytes. If data with a
  different number of bytes is received from the CAN bus, the appropriate
  read-functions will return a `SCI_LENGTH_ERR`.

`timeout`
  This is the timeout the object. The timeout is specified in
  milliseconds and can range from 0 to 32767. The timeout is useful for
  sci-functions that would otherwise never return in case of an error. An
  example for such a function is `sci_read`, this function waits for new
  data, if no new data arrives, it returns after the given timeout.
  Note that there are some sci-functions that do not need and do not use
  timeouts specified for a given object, an example for this is
  `sci_read_now`, this function returns immediately and does never wait
  for new data to arrive. Note also that remote-write objects
  (type `SCI_REMOTE_WRITE`) have no timeout. Any given timeout for this
  object-type is ignored.

`type`
  This is the type of the object, there are basically 4 types of
  objects which can be distinguished as read or write, remote or not-remote
  objects. These types are described in with the `sci_Object_Type` in
  this documentation.

`userp`
  This is an arbitrary pointer that is stored in the sci_Object. If you don't
  need this, just set this to `NULL`.

return value
  This function returns `SCI_NOTHING` in case of success.
  If wrong parameters were given, it returns the `SCI_ERROR`-flag.
  `SCI_EXISTS` signals that there was already an sci-object defined
  for the given CAN-id. If the new object properties do not match the ones of the
  already defined object, `SCI_ERROR` is returned, too. In this case
  the error-code that can be requested with the `sci_get_errcode()` function
  shows this first object property that did not match (e.g.
  `SCI_LENGTH_ERR`: the lengths were different).

.. index::
   single: sci_dup_object

sci_dup_object
--------------

::

  sci_Return sci_dup_object(sci_Struc *s_struc, sci_Object **dup_object,
  			  sci_Object *object, void *userp)
  

This function duplicates an existing sci-object. The second sci-object
has exactly the same properties as the original object. However, the user part
of the sci-object structure is duplicated and is independent from the user-part
of the original object. Both sci-objects, the old and the new one can then
be used to read or to write to a certain CAN-object. There is, from the users
point of view, no difference between the original and the duplicated object.
Each object can be deleted separately without interference with the other
one. There is only one point, were a difference is made between duplicated
objects, that is the *event-object* mechanism. Event-objects are used
to either start a user-defined callback function or to make
`sci_queue_read()` return. Both, the callback-function and
`sci_queue_read()` get a pointer to the sci-object where the event took
place. Since it is possible that one CAN-object has several associated
duplicated sci-objects, a decision has to be made which one is returned for
the *event*-mechanism. This object is defined with the
`sci_set_callback` - function. For a given set of duplicated objects, only
one can be the event-object.

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`dup_object`
  This is the address of a pointer to an sci-object. After
  successful execution of this function the pointer points to the new created
  sci_Object.

`object`
  This is the address of a pointer to an sci-object. After
  successful execution of this function the pointer points to the new created
  sci_Object.

`userp`
  This is an arbitrary pointer that is stored in the duplicated sci_Object. If
  you don't need this, just set this to `NULL`.

return value
  This function returns `SCI_NOTHING` in case of success or
  `SCI_ERROR` in case of a parameter error (e.g. when `object`
  is a `NULL` pointer).

.. index::
   single: sci_delete_object

sci_delete_object
-----------------

::

  sci_Return sci_delete_object(sci_Struc *s_struc, sci_Object **object);
  
This function deletes an sci-object. It removes the internal `sci_Object`-
structure and makes the CAN-id on the CAN interface available again. When
this function is performed on duplicated objects, the other duplicated object
for the same CAN-object remain unchanged.

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`object`
  This is the address of a pointer to an sci-object. After
  successful execution, the internal object-structure is deleted and the given
  pointer is changed to a `NULL` pointer.

return value
  This function returns `SCI_NOTHING` on success,
  `SCI_ERROR` in case of an error.

.. index::
   single: sci_set_inhibit

sci_set_inhibit
---------------

::

  sci_Return sci_set_inhibit(sci_Struc *s_struc, sci_Object *object,
                             unsigned long inhibit_time)
  

This function sets the inhibit-time for a CAN object. The main application
for inhibit-times is communication with slow CAN devices that are not able
to process CAN object's at the maximum possible speed. For example with a
1 MBit/s CAN line, a CAN frame can be physically sent about every 130
microseconds. If the other CAN participant can only process one frame every
1000 microseconds, inhibit-times can be used to limit the rate of transmission.
The inhibit-time is the minimal allowed time between two writes to a CAN-write
object. This function should only be applied to ordinary CAN-write objects.
The inhibit-time has only an effect when `sci_write_inhibit()` is
used instead of `sci_write()` to write to the CAN object. In current
implementations of sci the inhibit-time of a new created CAN object is 0 but
an application should not rely on that. See also the description of
`sci_write_inhibit()`.

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`object`
  This is the address of a pointer to an sci-object. The object
  must be an ordinary write-object (not a remote-write object).

`inhibit_time`
  This is the inhibit-time for the CAN object. Note that
  the inhibit-time (in opposition to timeout-times) is specified in microseconds.

return value
  This function returns `SCI_NOTHING` on success,
  `SCI_ERROR` in case of an error. Note that the attempt to set an
  inhibit-time on an object that is not an ordinary write-object causes an
  error.

.. index::
   single: sci_read_now

sci_read_now
------------

::

  sci_Return sci_read_now(sci_Struc *s_struc, sci_Object *object,
                          char *data);
  
In general, this function reads data from a can-object without waiting ('now').
This function can be applied to read and remote-read objects but not
*event-objects*. It's function,
however is different for each object-type:

- For ordinary read objects, this functions just reads data from the internal
  buffer that is always available on the CAN interface. The returned flags,
  however, indicate whether the data has already been read before or is really
  new.

- For remote-read objects, this function should be used in conjunction with
  `sci_write()`. `sci_write()` sends the remote-request while
  `sci_read_now` is used to read the reply. Although then the
  remote-request has already been sent, it may be, that `sci_read_now`
  has to wait some time for the answer. If the hardware of the answering CAN
  device is okay, the answer should be received within a millisecond. However,
  when there is an hardware error on the other CAN device, an answer will never
  come. For this reason, the function will return with an timeout-error after
  the timeout that was specified  (with `sci_init_object()`) with the
  given sci-object.

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`object`
  This is the sci-object that is to be read.

`data`
  This is a pointer to the area where the data has to be written.
  This pointer should be the address of a data-buffer that is defined in the
  user-program. 0 to 8 bytes are written on this address, the number depends on
  the length with which the object was defined (see also
  `sci_init_object()`).

return value
  This function returns `SCI_NOTHING` in case of success or
  `SCI_ERROR` in case of an error. It returns `SCI_OLD_DAT`
  when the data has already been read before, but the data is copied anyway to
  the address the user has given.

.. index::
   single: sci_read_new

sci_read_new
------------

::

  sci_Return sci_read_new(sci_Struc *s_struc, sci_Object *object,
                          char *data);
  
This function is similar to `sci_read_now` but it does not write to
the memory area `data` points to unless there was new data. Note that
this function, like `sci_read_now` does return immediately without
waiting. Note also, that this function works identical with `sci_read_now`
when it is used with remote-read objects. This function cannot be used
with *event-objects*.

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`object`
  This is the sci-object that is to be read.

`data`
  This is a pointer to the area where the data has to be written.
  This pointer should be the address of a data-buffer that is defined in the
  user-program. 0 to 8 bytes are written on this address, the number depends on
  the length with which the object was defined (see also
  `sci_init_object()`). The data is only written if it is found to be new.

return value
  This function returns `SCI_NOTHING` in case of success or
  `SCI_ERROR` in case of an error. It returns `SCI_OLD_DAT`
  when the data has already been read before. In this case, the data is not
  copied to the address the user has given.

.. index::
   single: sci_read

sci_read
--------

::

  sci_Return sci_read(sci_Struc *s_struc, sci_Object *object,
                      char *data);
  
This function reads data from a can-object, but it may wait for some time
(see also `sci_read_now()`). This function can be applied to read and
remote-read objects but not *event-objects*. It's function is
different for each of the two object-types:

- For ordinary read objects, this function returns when it finds data in the
  object's data buffer, that has not yet been read. If the data has already been
  read, the function waits for new data from the CAN bus. If no new data arrives
  after the object's timeout-time (specified with `sci_init_object()`)
  it returns with a timeout-status. The returned flags indicate whether the
  data is new (not yet read) or old (already read). Note that a timeout is
  not an error, but is just signalled by the `SCI_TMOUT`-flag, in this
  case the old data from the object's data buffer is returned.

- For remote-read objects, this function sends a remote-request and waits for
  the answer from another CAN device. If set up correctly, the other CAN device
  should send an answer together with new data back, this data is then returned
  by `sci_read()`. If no CAN device sends an answer within the object's
  timeout-time (specified with `sci_init_object()`), a timeout-error is
  returned. Note that this is (see above) a real sci-error and not a just a
  status.

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`object`
  This is the sci-object that is to be read.

`data`
  This is a pointer to the area where the data has to be written.
  This pointer should be the address of a data-buffer that is defined in the
  user-program. 0 to 8 bytes are written on this address, the number depends on
  the length with which the object was defined (see also
  `sci_init_object()`). The data is only written if it is found to be new.

return value
  This function returns `SCI_NOTHING` in case of success or
  `SCI_ERROR` in case of an error. Since this function waits for new
  data to arrive, it can return with a timeout when there was no new data within
  the timeout that was set for the object (see `sci_init_object()`). The
  timeout *is not* an error, a timeout causes the `SCI_TIMEOUT`
  flag to be returned, together with `SCI_OLD`, the returned data is
  just the old data that was found in the internal buffer from the previous
  transmission.

.. index::
   single: sci_queue_read

sci_queue_read
--------------

::

  sci_Return sci_queue_read(sci_Struc *s_struc, sci_Object **object,
                            char *data)
  

Please note that non-multitasking implementations of sci 
(e.g sci for embedded controller)
do not support `sci_queue_read` (see further below for datails).

`sci_queue_read` reads data from an *event-object*. This function *waits* until
an event takes place and returns the corresponding object-pointer and the new
data. 

Here are some advantages of using `sci_queue_read`:

- The objects do not have to be specified when the function is called. They
  are implicitly known; all event object that have *ever* been defined
  for the current thread (=process) are used.

- The number of objects is only limited to the number your hardware supports.
  Objects on different ports can be used (the port is defined with
  `sci_init_object()`).

- This function can be used on read *and* remote-read objects. An answer
  on a remote-request is also an event and is recognized when the remote-read
  object is also an *event-object*. Note that `sci_queue_read()`
  does not send the remote-request, that has to be done separately (with
  `sci_write()`.

- There is, in general, no timeout watch for *event-objects*. Any timeouts
  that were specified in the object's initialization, are ignored.
  `sci_queue_read()` will always wait for events *on all* event
  objects that are defined for the current thread (=process).

- Event-objects have to be initialized before the call `sci_queue_read()`
  by calling `sci_set_callback()`. In order to set-up event-objects
  for queue-read (instead of callback), the provided callback-function
  pointer for `sci_set_callback()` has to be a `NULL`-pointer.

- Since this function is based on the use of a semaphore, it is not available
  on single-tasking implementations of sci, like the MS-DOS implementation.

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`object`
  This is the address to a pointer where the sci-object pointer of
  the object is stored, where the event was detected.

`data`
  This is a pointer to the area where the data has to be written.
  This pointer should be the address of a data-buffer that is defined in the
  user-program. 0 to 8 bytes are written on this address, the number depends on
  the length with which the object was defined (see also
  `sci_init_object()`). The data is only written if it is found to be new.

return value
  This function returns `SCI_NOTHING` in case of success or
  `SCI_ERROR` in case of an error. It's return-codes are identical
  to the return-codes of `sci_read()` except that no timeouts can occur.

.. index::
   single: sci_write

sci_write
---------

::

  sci_Return sci_write(sci_Struc *s_struc, sci_Object *object, char *data);
  
This function writes data to a sci-object. This function can be applied to
write, remote-write and remote-read objects. It's function however is
different for each object-type:

- For ordinary write objects, this function writes data to the CAN bus. It
  depends on your implementation of sci whether the actual writing is done
  immediately or whether your hardware writes the data later independently
  from your program. If data is written immediately, `sci_write()`
  can detect when the writing failed and return an appropriate error-code.
  If data is written later, errors cannot be detected immediately, but only
  when `sci_write()` is called again. In this case a previously failed
  write will case `sci_write()` to return an error.

- For remote-write objects, data is just written to the object's data buffer.
  The data will only be sent to the CAN bus when a remote-request is received.
  This physical sending will be performed by the CAN hardware, independently
  of the software.

- For remote-read objects, just a remote-request is sent. The data parameter is
  ignored in this case. In order to receive the answer from another CAN-device
  for the remote-request you have to use `sci_read_now()` or
  the one of the two event-object mechanisms (for more details on this see also
  `sci_set_callback()` and `sci_queue_read()`).

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`object`
  This is the sci-object that is to be written to.

`data`
  This is a pointer to the area from where the data has to be read.
  This pointer should be the address of a data-buffer that is defined in the
  user-program. 0 to 8 bytes are written, this depends on the object's length
  which was defined with `sci_init_object()`. If `sci_write()` is used
  with remote-read objects, the `data`-parameter is ignored.

return value
  This function returns `SCI_NOTHING` in case of success or
  `SCI_ERROR` in case of an error.

.. index::
   single: sci_write_inhibit

sci_write_inhibit
-----------------

::

  sci_Return sci_write_inhibit(sci_Struc *s_struc, sci_Object *object,
                               char *data, unsigned long *rest_time)
  

This function is similar to `sci_write()`. It writes data to a
sci-object and can only be applied to ordinary write-objects.
`sci_write_inhibit()` should be used in conjunction with
`sci_set_inhibit()` which defines an inhibit-time for a single
CAN-object (note that upon creation of a CAN-write object, it's inhibit-time
is 0). `sci_write_inhibit()` fails when the time since the last write
to the CAN-object is less than the inhibit-time for that object. In this case,
it returns the time that the user has to wait, before he is allowed to write
again to the object. The purpose of this function is communication with slow
CAN participants that can only handle a certain number of CAN frames per
second (See also the description of `sci_set_inhibit()`). Note that
this function does not wait itself when the inhibit-time has not yet passed
but returns immediately without writing in this case. It is the task of the
user-program to wait the right amount of time.

Parameters and return-codes:

`s_struc`
  This is the sci-structure, created by `sci_open()`

`object`
  This is the sci-object that is to be written to. This must be
  an ordinary write-object.

`data`
  This is a pointer to the area from where the data has to be read.
  This pointer should be the address of a data-buffer that is defined in the
  user-program. 0 to 8 bytes are written, this depends on the object's length
  which was defined with `sci_init_object()`.

`rest_time`
  This is the time the user program has yet to wait before
  it can write to the CAN object again. The time is written to a variable of
  the type `unsigend int`, whose address is given by this parameter.
  This variable should only be evaluated, when `sci_write_inhibit()`
  returns `SCI_WAIT` in it's return-value. Note that the time discussed
  here is given in microseconds.

return value
  This function returns `SCI_NOTHING` in case of success or
  `SCI_ERROR` in case of an error. If the writing did not take place
  because the time since the last write was smaller than the inhibit-time,
  the `SCI_WAIT`-flag is returned.

For faster browsing, not all history is shown. View entire blame