ant-wireless 0.1.0.pre.20210617213631 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 47f23b13571d44d37275d309e73bf1b3b1d3b4f7e3c952f95fdf5b73321412b1
4
- data.tar.gz: 6bbccd101666ef42d12eab3d9b3d9e653634d97e19d9042f0c8282d74caf3fcb
3
+ metadata.gz: 0440d58876178ab22b480c72d95830474b407f7b1b366e518a7733a02abdd857
4
+ data.tar.gz: 2e0eb9be083381e57df2b13843894c33f43a957bff10a30fd06654fee41a5085
5
5
  SHA512:
6
- metadata.gz: 3cfbf1870872f9747df428d3ac4be4dd71b857bf47beb763f3d30fa517134b5d509e895ed975307b26de7936cee40dfc83f7b938e11679e61bf9e002d058acfb
7
- data.tar.gz: e7831b872fabbd850a946c88d053edc604aff86652e0efc6ffee9e593f92e5c52216a7382520765f2793a1e728b4457335ef3b9a999ec3d3eaa00699fdc89c2a
6
+ metadata.gz: 8237b0332974c4bc1afc2697b4502bb0048dbc00e6caf3ca4f004bc71a0f854fa997b0239d961dd0a0681dbeb3d3bbc370407c4900812233c6ae0a00fef7dbb1
7
+ data.tar.gz: e2e8f4dff3fc5d60181bd1b7a9f8fa3b5e7683d0c56243ffa0c4645cccc2b1692f738e39fc7f09ea63affaa6d126e4e9a254efbcbb624df14f811a78ccf17e72
checksums.yaml.gz.sig ADDED
Binary file
data/History.md CHANGED
@@ -1,5 +1,16 @@
1
1
  # Release History for ruby-ant
2
2
 
3
3
  ---
4
+ ## v0.2.0 [2021-09-22] Michael Granger <ged@FaerieMUD.org>
4
5
 
6
+ Enhancements:
7
+
8
+ - Add channel period, search timeout, and introspection methods
9
+ - Add Ant.initialized? predicate
10
+ - Make the default response and event callback modules more useful.
11
+
12
+
13
+ ## v0.1.0 [2021-08-26] Michael Granger <ged@FaerieMUD.org>
14
+
15
+ First release.
5
16
 
data/README.md CHANGED
@@ -20,8 +20,13 @@ manner.
20
20
 
21
21
  ## Prerequisites
22
22
 
23
- * Ruby
24
- * Garmin USB ANT Stick (https://buy.garmin.com/en-US/US/p/10997/pn/010-01058-00)
23
+ * Ruby 2.7.x or later
24
+ * [Garmin USB ANT Stick][antstick]
25
+ * [ANT SDK][antsdk]
26
+
27
+ Note that we had trouble compiling the latest ANT SDK on some platforms, so we are currently using a modified version of it with a reworked build system for MacOS and FreeBSD. That is available under the same licensing terms at:
28
+
29
+ https://github.com/RavnGroup/Garmin-ANT-SDK
25
30
 
26
31
 
27
32
  ## Installation
@@ -52,6 +57,12 @@ This task will install dependencies, and do any other necessary setup for develo
52
57
 
53
58
  ## License
54
59
 
60
+ Portions of this code are from StaticCling, and are used under the
61
+ terms of the 3-Clause BSD License. Specifics can be found in the
62
+ appropriate files.
63
+
64
+ This software is:
65
+
55
66
  Copyright (c) 2021, Ravn Group
56
67
 
57
68
  Permission is hereby granted, free of charge, to any person obtaining
@@ -76,4 +87,5 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
76
87
 
77
88
  [ant]: https://www.thisisant.com/
78
89
  [antstick]: https://buy.garmin.com/en-US/US/p/10997/pn/010-01058-00
90
+ [antsdk]: https://www.thisisant.com/developer/resources/downloads/#software_tab
79
91
 
@@ -225,6 +225,17 @@ rant_s_init( int argc, VALUE *argv, VALUE _module )
225
225
  }
226
226
 
227
227
 
228
+ static VALUE
229
+ rant_s_initialized_p( VALUE _module )
230
+ {
231
+ #ifdef HAVE_ANT_ISINITIALIZED
232
+ const bool initialized = ANT_IsInitialized();
233
+ return initialized ? Qtrue : Qfalse;
234
+ #else
235
+ rb_notimplement();
236
+ #endif
237
+ }
238
+
228
239
 
229
240
  /*
230
241
  * call-seq:
@@ -291,7 +302,7 @@ rant_s_set_network_key( VALUE _module, VALUE network_number, VALUE key )
291
302
  }
292
303
 
293
304
  if ( !ANT_SetNetworkKey(ucNetNumber, (unsigned char *)pucKey) ) {
294
- rb_raise( rb_eRuntimeError, "could not set the network key." );
305
+ rant_log( "error", "could not set the network key." );
295
306
  }
296
307
 
297
308
  return Qtrue;
@@ -463,6 +474,56 @@ rant_s_on_response( int argc, VALUE *argv, VALUE module )
463
474
  }
464
475
 
465
476
 
477
+ /*
478
+ * call-seq:
479
+ * Ant.request_capabilities
480
+ *
481
+ * Request the current ANT device's capabilities. These will be delivered
482
+ * via a callback to the #on_capabilities response callback, which by default
483
+ * extracts them into a Hash which is stored at Ant.capabilities.
484
+ *
485
+ */
486
+ static VALUE
487
+ rant_s_request_capabilities( VALUE module )
488
+ {
489
+ bool rval = ANT_RequestMessage( 0, MESG_CAPABILITIES_ID );
490
+ return rval ? Qtrue : Qfalse;
491
+ }
492
+
493
+
494
+ /*
495
+ * call-seq:
496
+ * Ant.request_serial_num
497
+ *
498
+ * Request the current ANT device's serial number. The result will be delivered
499
+ * via a callback to the #on_get_serial_num response callback, which by default
500
+ * extracts it and stores it at Ant.serial_number.
501
+ *
502
+ */
503
+ static VALUE
504
+ rant_s_request_serial_num( VALUE module )
505
+ {
506
+ bool rval = ANT_RequestMessage( 0, MESG_GET_SERIAL_NUM_ID );
507
+ return rval ? Qtrue : Qfalse;
508
+ }
509
+
510
+
511
+ /*
512
+ * call-seq:
513
+ * Ant.request_version
514
+ *
515
+ * Request the current device's ANT version. The result will be delivered
516
+ * via a callback to the #on_version response callback, which by default
517
+ * extracts it and stores it at Ant.hardware_version.
518
+ *
519
+ */
520
+ static VALUE
521
+ rant_s_request_version( VALUE module )
522
+ {
523
+ bool rval = ANT_RequestMessage( 0, MESG_VERSION_ID );
524
+ return rval ? Qtrue : Qfalse;
525
+ }
526
+
466
527
 
467
528
  /*
468
529
  * call-seq:
@@ -490,7 +551,7 @@ Init_ant_ext()
490
551
  /*
491
552
  * Document-module: Ant
492
553
  *
493
- * This is an extension for using the ANT ultra-low power wireless protocol via
554
+ * This is an extension for using the ANT ultra-low power wireless protocol via
494
555
  * the Garmin USB ANT Stick. ANT can be used to send information
495
556
  * wirelessly from one device to another device, in a robust and flexible
496
557
  * manner.
@@ -508,6 +569,7 @@ Init_ant_ext()
508
569
  rb_define_singleton_method( rant_mAnt, "device_serial_number", rant_s_device_serial_number, 0 );
509
570
 
510
571
  rb_define_singleton_method( rant_mAnt, "init", rant_s_init, -1 );
572
+ rb_define_singleton_method( rant_mAnt, "initialized?", rant_s_initialized_p, 0 );
511
573
  // rb_define_singleton_method( rant_mAnt, "init_ext", rant_s_init_ext, 4 );
512
574
  rb_define_singleton_method( rant_mAnt, "close", rant_s_close, 0 );
513
575
  rb_define_singleton_method( rant_mAnt, "reset", rant_s_reset, 0 );
@@ -521,6 +583,9 @@ Init_ant_ext()
521
583
  rb_define_singleton_method( rant_mAnt, "on_response", rant_s_on_response, -1 );
522
584
  // EXPORT void ANT_UnassignAllResponseFunctions(); //Unassigns all response functions
523
585
 
586
+ rb_define_singleton_method( rant_mAnt, "request_capabilities", rant_s_request_capabilities, 0 );
587
+ rb_define_singleton_method( rant_mAnt, "request_serial_num", rant_s_request_serial_num, 0 );
588
+ rb_define_singleton_method( rant_mAnt, "request_version", rant_s_request_version, 0 );
524
589
 
525
590
  rb_define_singleton_method( rant_mAnt, "log_directory=", rant_s_log_directory_eq, 1 );
526
591
 
@@ -537,6 +602,7 @@ Init_ant_ext()
537
602
  EXPOSE_CONST( ANT_EXT_STRING_SIZE );
538
603
  EXPOSE_CONST( ANT_EXT_MESG_BITFIELD_DEVICE_ID );
539
604
  EXPOSE_CONST( ANT_EXT_MESG_BIFIELD_EXTENSION );
605
+ rb_define_const( rant_mAnt, "ANT_EXT_MESG_BITFIELD_EXTENSION", INT2FIX(ANT_EXT_MESG_BIFIELD_EXTENSION) );
540
606
  EXPOSE_CONST( ANT_EXT_MESG_BITFIELD_OVERWRITE_SHARED_ADR );
541
607
  EXPOSE_CONST( ANT_EXT_MESG_BITFIELD_TRANSMISSION_TYPE );
542
608
 
@@ -618,6 +684,9 @@ Init_ant_ext()
618
684
  EXPOSE_CONST( CAPABILITIES_SELECTIVE_DATA_UPDATE_ENABLED );
619
685
  EXPOSE_CONST( CAPABILITIES_ENCRYPTED_CHANNEL_ENABLED );
620
686
 
687
+ // Not in the header; this is taken from 9.5.7.4, ANT Message Protocol and Usage v5.1
688
+ rb_define_const( rant_mAnt, "CAPABILITIES_RFACTIVE_NOTIFICATION_ENABLED", INT2FIX(0) );
689
+
621
690
  EXPOSE_CONST( CHANNEL_NUMBER_MASK );
622
691
  EXPOSE_CONST( SEQUENCE_NUMBER_MASK );
623
692
  EXPOSE_CONST( SEQUENCE_NUMBER_ROLLOVER );
@@ -128,6 +128,11 @@ rant_channel_init( VALUE self, VALUE channel_number, VALUE channel_type, VALUE n
128
128
  rb_iv_set( self, "@network_number", network_number );
129
129
  rb_iv_set( self, "@extended_options", extended_options );
130
130
 
131
+ rb_iv_set( self, "@device_type", Qnil );
132
+ rb_iv_set( self, "@device_number", Qnil );
133
+ rb_iv_set( self, "@transmission_type", Qnil );
134
+ rb_iv_set( self, "@rf_frequency", Qnil );
135
+
131
136
  rb_hash_aset( registry, channel_number, self );
132
137
 
133
138
  return self;
@@ -173,8 +178,8 @@ rant_channel_set_channel_id( int argc, VALUE *argv, VALUE self )
173
178
  rb_scan_args( argc, argv, "31", &device_number, &device_type, &transmission_type, &timeout );
174
179
 
175
180
  usDeviceNumber = NUM2USHORT( device_number );
176
- ucDeviceType = NUM2USHORT( device_type );
177
- ucTransmissionType = NUM2USHORT( transmission_type );
181
+ ucDeviceType = NUM2CHR( device_type );
182
+ ucTransmissionType = NUM2CHR( transmission_type );
178
183
 
179
184
  if ( RTEST(timeout) )
180
185
  ulResponseTime = NUM2UINT( timeout );
@@ -186,13 +191,114 @@ rant_channel_set_channel_id( int argc, VALUE *argv, VALUE self )
186
191
  rb_raise( rb_eRuntimeError, "Failed to set the channel id." );
187
192
  }
188
193
 
194
+ rb_iv_set( self, "@device_type", device_type );
195
+ rb_iv_set( self, "@device_number", device_number );
196
+ rb_iv_set( self, "@transmission_type", transmission_type );
197
+
198
+ return Qtrue;
199
+ }
200
+
201
+
202
+ /*
203
+ * call-seq:
204
+ * channel.set_channel_period( period, timeout=0 )
205
+ *
206
+ * This message configures the messaging +period+ of a specific channel where:
207
+ * Messaging period = channel period time +period+ * 32768.
208
+ *
209
+ * E.g.: To send or receive a message at 4Hz, set the channel period to 8192 (32768/4).
210
+ *
211
+ * Note: The minimum acceptable channel period is difficult to specify as it is
212
+ * system dependent and depends on the number of configured channels and their use.
213
+ * Caution should be used to appropriately test the system when high data rates are
214
+ * used, especially in combination with multiple channels.
215
+ *
216
+ */
217
+ static VALUE
218
+ rant_channel_set_channel_period( int argc, VALUE *argv, VALUE self )
219
+ {
220
+ rant_channel_t *ptr = rant_get_channel( self );
221
+ VALUE period, timeout;
222
+ unsigned int ulResponseTime = 0;
223
+ unsigned short usMesgPeriod;
224
+ bool result;
225
+
226
+ rb_scan_args( argc, argv, "11", &period, &timeout );
227
+
228
+ usMesgPeriod = NUM2USHORT( period );
229
+ if ( RTEST(timeout) )
230
+ ulResponseTime = NUM2UINT( timeout );
231
+
232
+ result = ANT_SetChannelPeriod_RTO( ptr->channel_num, usMesgPeriod, ulResponseTime );
233
+
234
+ if ( !result )
235
+ rb_raise( rb_eRuntimeError, "Failed to set the channel period." );
236
+
237
+ return Qtrue;
238
+ }
239
+
240
+
241
+ /*
242
+ * call-seq:
243
+ * channel.set_channel_search_timeout( search_timeout, timeout=0 )
244
+ *
245
+ * Configure the length of time that the receiver will search for a channel
246
+ * before timing out. Note that a value of zero will disable high priority
247
+ * search mode, and a value of 255 sets an infinite search time-out. The
248
+ * exception to this is the AP1 module, which has only a high priority search
249
+ * mode. For AP1 only, a value of 0 is an immediate search timeout, and a value
250
+ * of 255 corresponds to approximately 10.5 minutes.
251
+ *
252
+ */
253
+ static VALUE
254
+ rant_channel_set_channel_search_timeout( int argc, VALUE *argv, VALUE self )
255
+ {
256
+ rant_channel_t *ptr = rant_get_channel( self );
257
+ VALUE search_timeout, timeout;
258
+ unsigned int ulResponseTime = 0;
259
+ unsigned char ucSearchTimeout;
260
+ bool result;
261
+
262
+ rb_scan_args( argc, argv, "11", &search_timeout, &timeout );
263
+
264
+ ucSearchTimeout = NUM2CHR( search_timeout );
265
+ if ( RTEST(timeout) )
266
+ ulResponseTime = NUM2UINT( timeout );
267
+
268
+ result = ANT_SetChannelSearchTimeout_RTO( ptr->channel_num, ucSearchTimeout, ulResponseTime );
269
+
270
+ if ( !result )
271
+ rb_raise( rb_eRuntimeError, "Failed to set the channel search timeout." );
272
+
273
+ return Qtrue;
274
+ }
275
+
276
+
277
+ /*
278
+ * call-seq:
279
+ * channel.set_channel_rf_freq( frequency )
280
+ *
281
+ * Set the ANT RF +frequency+.
282
+ *
283
+ */
284
+ static VALUE
285
+ rant_channel_set_channel_rf_freq( VALUE self, VALUE frequency )
286
+ {
287
+ rant_channel_t *ptr = rant_get_channel( self );
288
+ unsigned short ucRFFreq = NUM2USHORT( frequency );
289
+
290
+ if ( ucRFFreq > 124 ) {
291
+ rb_raise( rb_eArgError, "frequency must be between 0 and 124." );
292
+ }
293
+
294
+ ANT_SetChannelRFFreq( ptr->channel_num, ucRFFreq );
295
+
296
+ rb_iv_set( self, "@rf_frequency", frequency );
297
+
189
298
  return Qtrue;
190
299
  }
191
300
 
192
301
 
193
- // ANT_SetChannelPeriod_RTO(UCHAR ucANTChannel_, USHORT usMesgPeriod_, ULONG ulResponseTime_);
194
- // ANT_SetChannelSearchTimeout_RTO(UCHAR ucANTChannel_, UCHAR ucSearchTimeout_, ULONG ulResponseTime_);
195
- // ANT_SetChannelRFFreq_RTO(UCHAR ucANTChannel_, UCHAR ucRFFreq_, ULONG ulResponseTime_);
196
302
 
197
303
 
198
304
  /*
@@ -450,29 +556,6 @@ rant_channel_send_broadcast_data( VALUE self, VALUE data )
450
556
  }
451
557
 
452
558
 
453
- /*
454
- * call-seq:
455
- * channel.set_channel_rf_freq( frequency )
456
- *
457
- * Set the ANT RF +frequency+.
458
- *
459
- */
460
- static VALUE
461
- rant_channel_set_channel_rf_freq( VALUE self, VALUE frequency )
462
- {
463
- rant_channel_t *ptr = rant_get_channel( self );
464
- unsigned short ucRFFreq = NUM2USHORT( frequency );
465
-
466
- if ( ucRFFreq > 124 ) {
467
- rb_raise( rb_eArgError, "frequency must be between 0 and 124." );
468
- }
469
-
470
- ANT_SetChannelRFFreq( ptr->channel_num, ucRFFreq );
471
-
472
- return Qtrue;
473
- }
474
-
475
-
476
559
  void
477
560
  init_ant_channel()
478
561
  {
@@ -501,11 +584,15 @@ init_ant_channel()
501
584
  rb_attr( rant_cAntChannel, rb_intern("network_number"), 1, 0, 0 );
502
585
  rb_attr( rant_cAntChannel, rb_intern("extended_options"), 1, 0, 0 );
503
586
 
587
+ rb_attr( rant_cAntChannel, rb_intern("device_number"), 1, 0, 0 );
588
+ rb_attr( rant_cAntChannel, rb_intern("device_type"), 1, 0, 0 );
589
+ rb_attr( rant_cAntChannel, rb_intern("transmission_type"), 1, 0, 0 );
590
+ rb_attr( rant_cAntChannel, rb_intern("rf_frequency"), 1, 0, 0 );
591
+
504
592
  rb_define_method( rant_cAntChannel, "set_channel_id", rant_channel_set_channel_id, -1 );
505
- // rb_define_method( rant_cAntChannel, "set_channel_period",
506
- // rant_channel_set_channel_period, -1 );
507
- // rb_define_method( rant_cAntChannel, "set_channel_search_timeout",
508
- // rant_channel_set_channel_search_timeout, -1 );
593
+ rb_define_method( rant_cAntChannel, "set_channel_period", rant_channel_set_channel_period, -1 );
594
+ rb_define_method( rant_cAntChannel, "set_channel_search_timeout",
595
+ rant_channel_set_channel_search_timeout, -1 );
509
596
  rb_define_method( rant_cAntChannel, "set_channel_rf_freq", rant_channel_set_channel_rf_freq, 1 );
510
597
 
511
598
  rb_define_method( rant_cAntChannel, "open", rant_channel_open, -1 );
@@ -14,6 +14,7 @@ have_header( 'ruby/thread.h' ) or
14
14
  abort "Your Ruby is too old!"
15
15
 
16
16
  have_func( 'ANT_Init', 'libant.h' )
17
+ have_func( 'ANT_IsInitialized', 'libant.h' )
17
18
  have_func( 'ANT_LibVersion', 'libant.h' )
18
19
  have_func( 'ANT_GetDeviceSerialNumber', 'libant.h' )
19
20
 
@@ -13,12 +13,8 @@ require 'ant/mixins'
13
13
  # Refs:
14
14
  # * 9.5.6.1 Channel Response / Event (0x40) [ANT Message Protocol and Usage, Rev 5.1]
15
15
  module Ant::Channel::EventCallbacks
16
- extend Loggability
17
- include Ant::DataUtilities
18
-
19
-
20
- # Loggability API -- send logs to the Ant logger
21
- log_to :ant
16
+ extend Loggability,
17
+ Ant::DataUtilities
22
18
 
23
19
 
24
20
  # Mapping of response message IDs to handler methods
@@ -51,17 +47,8 @@ module Ant::Channel::EventCallbacks
51
47
  SEQUENCE_NUMBER_MASK = 0xE0
52
48
 
53
49
 
54
- ### Default callback hook -- handles event callbacks.
55
- def handle_event_callback( channel_num, event_id, data )
56
- handler_method = HANDLER_METHODS[ event_id ] or
57
- raise "Unhandled channel event %p" % [ event_id ]
58
-
59
- if self.respond_to?( handler_method )
60
- self.public_send( handler_method, channel_num, data )
61
- else
62
- Ant::Channel::EventCallbacks.log_event_callback( channel_num, handler_method, event_id, data )
63
- end
64
- end
50
+ # Loggability API -- send logs to the Ant logger
51
+ log_to :ant
65
52
 
66
53
 
67
54
  ### Log the channel event by default.
@@ -75,13 +62,25 @@ module Ant::Channel::EventCallbacks
75
62
  end
76
63
 
77
64
 
65
+ ### Default callback hook -- handles event callbacks.
66
+ def handle_event_callback( channel_num, event_id, data )
67
+ handler_method = Ant::Channel::EventCallbacks::HANDLER_METHODS[ event_id ] or
68
+ raise "Unhandled channel event %p" % [ event_id ]
69
+
70
+ if self.respond_to?( handler_method )
71
+ self.public_send( handler_method, channel_num, data )
72
+ else
73
+ Ant::Channel::EventCallbacks.log_event_callback( channel_num, handler_method, event_id, data )
74
+ end
75
+ end
76
+
77
+
78
78
  ### Handle an TX event.
79
79
  def on_event_tx( channel_num, data )
80
- # self.log.info "Broadcast message on channel %d was transmitted." % [ channel_num ]
81
-
82
- # data = SecureRandom.bytes( 8 )
83
- # self.log.debug "Sending our own broadcast data: %p." % [ data ]
84
- # self.send_broadcast_data( data )
80
+ channel = Ant::Channel.registry[ channel_num ]
81
+ self.log.debug "%p ready for transmission." % [ channel ]
82
+ ident = [ 1, 33 ].pack( "CC" )
83
+ channel.send_broadcast_data( ident )
85
84
  end
86
85
 
87
86
 
@@ -139,18 +138,27 @@ module Ant::Channel::EventCallbacks
139
138
  end
140
139
 
141
140
 
142
- # def on_event_rx_flag_acknowledged( channel_num, data )
143
- #
144
- # end
141
+ def on_event_rx_flag_acknowledged( channel_num, data )
142
+ flags = data.bytes[ 9 ]
143
+ if flags & Ant::ANT_EXT_MESG_BITFIELD_DEVICE_ID
144
+ usDeviceNumber = data.bytes[10] | (data.bytes[11] << 8)
145
+ ucDeviceType = data.bytes[12]
146
+ ucTransmissionType = data.bytes[13]
147
+ self.log.debug "Got an acknowledge on Chan ID(%d/%d/%d)" %
148
+ [usDeviceNumber, ucDeviceType, ucTransmissionType]
149
+ end
150
+
151
+ self.on_event_rx_acknowledged( channel_num, data )
152
+ end
153
+
145
154
 
146
- ### Handle an RX_FLAG_BURST_PACKET event.
147
155
  def on_event_rx_flag_burst_packet( channel_num, data )
148
156
  flags = data.bytes[ 9 ]
149
157
  if flags & Ant::ANT_EXT_MESG_BITFIELD_DEVICE_ID
150
158
  usDeviceNumber = data.bytes[10] | (data.bytes[11] << 8)
151
159
  ucDeviceType = data.bytes[12]
152
160
  ucTransmissionType = data.bytes[13]
153
- self.log.info "Got a burst on Chan ID(%d/%d/%d)" %
161
+ self.log.debug "Got a burst on Chan ID(%d/%d/%d)" %
154
162
  [usDeviceNumber, ucDeviceType, ucTransmissionType]
155
163
  end
156
164
 
@@ -158,14 +166,13 @@ module Ant::Channel::EventCallbacks
158
166
  end
159
167
 
160
168
 
161
- ### Handle an RX_FLAG_BROADCAST event.
162
169
  def on_event_rx_flag_broadcast( channel_num, data )
163
170
  flags = data.bytes[ 9 ]
164
171
  if flags & Ant::ANT_EXT_MESG_BITFIELD_DEVICE_ID
165
172
  usDeviceNumber = data.bytes[10] | (data.bytes[11] << 8)
166
173
  ucDeviceType = data.bytes[12]
167
174
  ucTransmissionType = data.bytes[13]
168
- self.log.info "Got a broadcast on Chan ID(%d/%d/%d)" %
175
+ self.log.debug "Got a broadcast on Chan ID(%d/%d/%d)" %
169
176
  [usDeviceNumber, ucDeviceType, ucTransmissionType]
170
177
  end
171
178
 
@@ -173,23 +180,21 @@ module Ant::Channel::EventCallbacks
173
180
  end
174
181
 
175
182
 
176
- # def on_event_rx_acknowledged( channel_num, data )
177
- #
178
- # end
183
+ def on_event_rx_acknowledged( channel_num, data )
184
+ self.log.debug "Acknowledged: Rx [%d]:\n%s" % [ data.bytes[0], Ant::DataUtilities.hexdump(data[1..9]) ]
185
+ end
179
186
 
180
187
 
181
- ### Handle an RX_BURST_PACKET event.
182
188
  def on_event_rx_burst_packet( channel_num, data )
183
189
  channel = (data.bytes[0] & CHANNEL_NUMBER_MASK) >> 5
184
190
  sequence_num = data.bytes[0] & SEQUENCE_NUMBER_MASK
185
191
 
186
- self.log.info "Burst (0x%02x): Rx: %d:\n%s" % [ channel, sequence_num, hexdump(data[1..8]) ]
192
+ self.log.debug "Burst (0x%02x): Rx: %d:\n%s" % [ channel, sequence_num, Ant::DataUtilities.hexdump(data[1..9]) ]
187
193
  end
188
194
 
189
195
 
190
- ### Handle an RX_BROADCAST event.
191
196
  def on_event_rx_broadcast( channel_num, data )
192
- self.log.info "Broadcast: Rx:\n%s" % [ hexdump(data[1..8]) ]
197
+ self.log.debug "Broadcast: Rx [%d]:\n%s" % [ data.bytes[0], Ant::DataUtilities.hexdump(data[1..9]) ]
193
198
  end
194
199
 
195
200
 
data/lib/ant/channel.rb CHANGED
@@ -9,6 +9,7 @@ require 'ant' unless defined?( Ant )
9
9
  class Ant::Channel
10
10
  extend Loggability
11
11
 
12
+
12
13
  # The default network number
13
14
  DEFAULT_NETWORK_NUMBER = 0
14
15
 
@@ -20,7 +21,8 @@ class Ant::Channel
20
21
  # Autoloads
21
22
  #
22
23
 
23
- autoload :EventCallbacks, 'ant/channel/event_callbacks'
24
+ require 'ant/channel/event_callbacks'
25
+ include Ant::Channel::EventCallbacks
24
26
 
25
27
 
26
28
  # Loggability API -- log to the Ant logger
@@ -31,6 +33,7 @@ class Ant::Channel
31
33
 
32
34
 
33
35
  ##
36
+ # :singleton-method: registry
34
37
  # Channel registry, keyed by channel number.
35
38
  singleton_class.attr_reader( :registry )
36
39
 
@@ -43,24 +46,68 @@ class Ant::Channel
43
46
 
44
47
 
45
48
  ### Set up the given +mod+ as the handler module for channel events.
46
- def set_event_handlers( mod=Ant::Channel::EventCallbacks )
47
- self.extend( mod )
48
- self.on_event( &self.method(:handle_event_callback) )
49
+ def set_event_handlers( object=self )
50
+ self.on_event( &object.method(:handle_event_callback) )
51
+ end
52
+
53
+
54
+ ### Return the ANT channel ID if one has been assigned.
55
+ def channel_id
56
+ device_number = self.device_number or return nil
57
+ device_type = self.device_type & 0x7f
58
+ pairing_bit = self.device_type & 0x80
59
+ transmission_type = self.transmission_type
60
+
61
+ return "%d/%d/%d%s" % [
62
+ device_number,
63
+ device_type,
64
+ transmission_type,
65
+ pairing_bit.nonzero? ? '+' : '',
66
+ ]
67
+ end
68
+
69
+
70
+ ### Return a human-readable description of the channel type.
71
+ def channel_type_description
72
+ case self.channel_type
73
+ when Ant::PARAMETER_RX_NOT_TX
74
+ return :slave
75
+ when Ant::PARAMETER_TX_NOT_RX
76
+ return :master
77
+ when Ant::PARAMETER_SHARED_CHANNEL
78
+ return :shared
79
+ when Ant::PARAMETER_NO_TX_GUARD_BAND
80
+ return :no_tx_guard_band
81
+ when Ant::PARAMETER_ALWAYS_RX_WILD_CARD_SEARCH_ID
82
+ return :always_rx_wild_card_search_id
83
+ when Ant::PARAMETER_RX_ONLY
84
+ return :rx_only
85
+ else
86
+ return nil
87
+ end
88
+ end
89
+
90
+
91
+ ### Returns +true+ if the channel is not closed.
92
+ def open?
93
+ return !self.closed?
49
94
  end
50
95
 
51
96
 
52
97
  ### Return a human-readable version of the object suitable for debugging.
53
98
  def inspect
54
- return "#<%p:%#x {%d} %#02x on network %d: %d%s>" % [
99
+ return "#<%p:%#x %s {%s} #%d @%dMHz on network %d%s>" % [
55
100
  self.class,
56
101
  self.object_id,
102
+ self.channel_type_description,
103
+ self.channel_id || '-',
57
104
  self.channel_number,
58
- self.channel_type,
105
+ self.rf_frequency + 2400,
59
106
  self.network_number,
60
- self.extended_options,
61
107
  self.closed? ? " (closed)" : "",
62
108
  ]
63
109
  end
64
110
 
65
111
  end # class Ant::Channel
66
112
 
113
+