Project

General

Profile

Revision 343

Added by Jason knichel over 16 years ago

changed the brace style and reformatted the files

View differences:

trunk/code/projects/libwireless/lib/wl_token_ring.c
67 67
void wl_token_ring_timeout_handler(void);
68 68
void wl_token_ring_response_handler(int frame, int received);
69 69
void wl_token_ring_receive_handler(char type, int source, unsigned char* packet,
70
							int length);
70
				   int length);
71 71
void wl_token_ring_cleanup(void);
72 72

  
73 73
/*Helper Functions*/
......
127 127
#endif
128 128

  
129 129
PacketGroupHandler wl_token_ring_handler =
130
		{WL_TOKEN_RING_GROUP, wl_token_ring_timeout_handler,
131
		wl_token_ring_response_handler, wl_token_ring_receive_handler,
132
		wl_token_ring_cleanup};
130
  {WL_TOKEN_RING_GROUP, wl_token_ring_timeout_handler,
131
   wl_token_ring_response_handler, wl_token_ring_receive_handler,
132
   wl_token_ring_cleanup};
133 133

  
134 134
/**
135 135
 * Initialize the token ring packet group and register it with the
136 136
 * wireless library. The robot will not join a token ring.
137 137
 **/
138
void wl_token_ring_register()
139
{
140
	if (wl_get_xbee_id() > 0xFF)
141
	{
142
		//Note: if this becomes an issue (unlikely), we could limit sensor information
143
		//to half a byte and use 12 bits for the id
144
		WL_DEBUG_PRINT("XBee ID must be single byte for token ring, is ");
145
		WL_DEBUG_PRINT_INT(wl_get_xbee_id());
146
		WL_DEBUG_PRINT(".\r\n");
147
		return;
148
	}
138
void wl_token_ring_register() {
139
  if (wl_get_xbee_id() > 0xFF) {
140
    //Note: if this becomes an issue (unlikely), we could limit sensor information
141
    //to half a byte and use 12 bits for the id
142
    WL_DEBUG_PRINT("XBee ID must be single byte for token ring, is ");
143
    WL_DEBUG_PRINT_INT(wl_get_xbee_id());
144
    WL_DEBUG_PRINT(".\r\n");
145
    return;
146
  }
149 147
	
150
	sensorMatrix = sensor_matrix_create();
151
	//add ourselves to the sensor matrix
152
	sensor_matrix_set_in_ring(sensorMatrix, wl_get_xbee_id(), 0);
148
  sensorMatrix = sensor_matrix_create();
149
  //add ourselves to the sensor matrix
150
  sensor_matrix_set_in_ring(sensorMatrix, wl_get_xbee_id(), 0);
153 151

  
154
	wl_register_packet_group(&wl_token_ring_handler);
152
  wl_register_packet_group(&wl_token_ring_handler);
155 153
}
156 154

  
157 155
/**
158 156
 * Removes the packet group from the wireless library.
159 157
 **/
160
void wl_token_ring_unregister()
161
{
162
	wl_unregister_packet_group(&wl_token_ring_handler);
158
void wl_token_ring_unregister() {
159
  wl_unregister_packet_group(&wl_token_ring_handler);
163 160
}
164 161

  
165 162
/**
......
175 172
 * measurement of the maximum BOM reading is needed.
176 173
 **/
177 174
void wl_token_ring_set_bom_functions(void (*on_function) (void),
178
	void (*off_function) (void), int (*max_bom_function) (void))
179
{
180
	bom_on_function = on_function;
181
	bom_off_function = off_function;
182
	get_max_bom_function = max_bom_function;
175
				     void (*off_function) (void), int (*max_bom_function) (void)) {
176
  bom_on_function = on_function;
177
  bom_off_function = off_function;
178
  get_max_bom_function = max_bom_function;
183 179
}
184 180

  
185 181
/**
186 182
 * Called to cleanup the token ring packet group.
187 183
 **/
188
void wl_token_ring_cleanup()
189
{
190
	sensor_matrix_destroy(sensorMatrix);
184
void wl_token_ring_cleanup() {
185
  sensor_matrix_destroy(sensorMatrix);
191 186
}
192 187

  
193 188
/**
194 189
 * Called approximately every quarter second by the wireless library.
195 190
 **/
196
void wl_token_ring_timeout_handler()
197
{
198
	//someone is not responding, assume they are dead
199
	if (deathDelay == 0)
200
	{
201
		//pass the token to the next robot if we think someone has died
202
		//also, declare that person dead, as long as it isn't us
203
		if (wl_token_next_robot != wl_get_xbee_id())
204
		{
205
			sensor_matrix_set_in_ring(sensorMatrix, wl_token_next_robot, 0);
206
			WL_DEBUG_PRINT("Robot ");
207
			WL_DEBUG_PRINT_INT(wl_token_next_robot);
208
			WL_DEBUG_PRINT(" has died.\r\n");
209
			wl_token_next_robot = -1;
210
			deathDelay = DEATH_DELAY;
211
		}
191
void wl_token_ring_timeout_handler() {
192
  //someone is not responding, assume they are dead
193
  if (deathDelay == 0) {
194
    //pass the token to the next robot if we think someone has died
195
    //also, declare that person dead, as long as it isn't us
196
    if (wl_token_next_robot != wl_get_xbee_id()) {
197
      sensor_matrix_set_in_ring(sensorMatrix, wl_token_next_robot, 0);
198
      WL_DEBUG_PRINT("Robot ");
199
      WL_DEBUG_PRINT_INT(wl_token_next_robot);
200
      WL_DEBUG_PRINT(" has died.\r\n");
201
      wl_token_next_robot = -1;
202
      deathDelay = DEATH_DELAY;
203
    }
212 204
		
213
		// we may have been dropped from the ring when this is received
214
		if (ringState == MEMBER)
215
			wl_token_pass_token();
216
	}
205
    // we may have been dropped from the ring when this is received
206
    if (ringState == MEMBER)
207
      wl_token_pass_token();
208
  }
217 209

  
218
	//we must start our own token ring, no one is responding to us
219
	if (joinDelay == 0)
220
	{
221
		if (sensor_matrix_get_joined(sensorMatrix) == 0)
222
		{
223
			WL_DEBUG_PRINT("Creating our own token ring, no robots seem to exist.\r\n");
224
			sensor_matrix_set_in_ring(sensorMatrix, wl_get_xbee_id(), 1);
225
			ringState = MEMBER;
226
			//this will make us pass the token to ourself
227
			//repeatedly, and other robots when they join
228
			deathDelay = DEATH_DELAY;
229
			wl_token_next_robot = wl_get_xbee_id();
230
		}
231
		else
232
		{
233
			WL_DEBUG_PRINT("Attempting to join the token ring again.\r\n");
234
			//attempt to rejoin with a random delay
235
			wl_token_ring_join();
236
			joinDelay = rand() / (RAND_MAX / JOIN_DELAY) + 1;
237
		}
238
	}
210
  //we must start our own token ring, no one is responding to us
211
  if (joinDelay == 0) {
212
    if (sensor_matrix_get_joined(sensorMatrix) == 0) {
213
      WL_DEBUG_PRINT("Creating our own token ring, no robots seem to exist.\r\n");
214
      sensor_matrix_set_in_ring(sensorMatrix, wl_get_xbee_id(), 1);
215
      ringState = MEMBER;
216
      //this will make us pass the token to ourself
217
      //repeatedly, and other robots when they join
218
      deathDelay = DEATH_DELAY;
219
      wl_token_next_robot = wl_get_xbee_id();
220
    } else {
221
      WL_DEBUG_PRINT("Attempting to join the token ring again.\r\n");
222
      //attempt to rejoin with a random delay
223
      wl_token_ring_join();
224
      joinDelay = rand() / (RAND_MAX / JOIN_DELAY) + 1;
225
    }
226
  }
239 227

  
240
	if (deathDelay >= 0)
241
		deathDelay--;
242
	if (joinDelay >= 0)
243
		joinDelay--;
244
	if (bom_on_count >= 0)
245
		bom_on_count++;
228
  if (deathDelay >= 0)
229
    deathDelay--;
230
  if (joinDelay >= 0)
231
    joinDelay--;
232
  if (bom_on_count >= 0)
233
    bom_on_count++;
246 234
}
247 235

  
248 236
/**
......
251 239
 * @param frame the frame number assigned when the packet was sent
252 240
 * @param received 1 if the packet was received, 0 otherwise
253 241
 **/
254
void wl_token_ring_response_handler(int frame, int received)
255
{
256
	if (!received)
257
	{
258
		WL_DEBUG_PRINT("FAILED.\r\n");
259
	}
242
void wl_token_ring_response_handler(int frame, int received) {
243
  if (!received) {
244
    WL_DEBUG_PRINT("FAILED.\r\n");
245
  }
260 246
}
261 247

  
262 248
/**
......
267 253
 * @param length the length of the packet in bytes
268 254
 **/
269 255
void wl_token_ring_receive_handler(char type, int source, unsigned char* packet,
270
							int length)
271
{
272
	switch (type)
273
	{
274
		case WL_TOKEN_PASS:
275
			if (length < 1)
276
			{
277
				WL_DEBUG_PRINT("Malformed Token Pass packet received.\r\n");
278
				return;
279
			}
280
			wl_token_pass_receive(source, packet[0], packet + 1, length - 1);
281
			break;
282
		case WL_TOKEN_BOM_ON:
283
			//add the robot to the sensor matrix if it is not already there
284
			wl_token_bom_on_receive(source);
285
			break;
286
		case WL_TOKEN_JOIN:
287
			wl_token_join_receive(source);
288
			break;
289
		case WL_TOKEN_JOIN_ACCEPT:
290
			wl_token_join_accept_receive(source);
291
			break;
292
		default:
293
			WL_DEBUG_PRINT("Unimplemented token ring packet received.\r\n");
294
			break;
295
	}
256
				   int length) {
257
  switch (type) {
258
  case WL_TOKEN_PASS:
259
    if (length < 1) {
260
      WL_DEBUG_PRINT("Malformed Token Pass packet received.\r\n");
261
      return;
262
    }
263
    wl_token_pass_receive(source, packet[0], packet + 1, length - 1);
264
    break;
265
  case WL_TOKEN_BOM_ON:
266
    //add the robot to the sensor matrix if it is not already there
267
    wl_token_bom_on_receive(source);
268
    break;
269
  case WL_TOKEN_JOIN:
270
    wl_token_join_receive(source);
271
    break;
272
  case WL_TOKEN_JOIN_ACCEPT:
273
    wl_token_join_accept_receive(source);
274
    break;
275
  default:
276
    WL_DEBUG_PRINT("Unimplemented token ring packet received.\r\n");
277
    break;
278
  }
296 279
}
297 280

  
298 281
/**
......
300 283
 * if no token ring exists. The token ring uses global and robot to robot
301 284
 * packets, and does not rely on any PAN.
302 285
 **/
303
void wl_token_ring_join()
304
{
305
	WL_DEBUG_PRINT("Joining the token ring.\r\n");
306
	ringState = JOINING;
307
	joinDelay = DEATH_DELAY * 2;
308
	wl_send_global_packet(WL_TOKEN_RING_GROUP, WL_TOKEN_JOIN,
309
		NULL, 0, 0);
286
void wl_token_ring_join() {
287
  WL_DEBUG_PRINT("Joining the token ring.\r\n");
288
  ringState = JOINING;
289
  joinDelay = DEATH_DELAY * 2;
290
  wl_send_global_packet(WL_TOKEN_RING_GROUP, WL_TOKEN_JOIN,
291
			NULL, 0, 0);
310 292
}
311 293

  
312 294
/**
......
314 296
 * alerting others of its location, but continues storing the
315 297
 * locations of other robots.
316 298
 **/
317
void wl_token_ring_leave()
318
{
319
	ringState = LEAVING;
299
void wl_token_ring_leave() {
300
  ringState = LEAVING;
320 301
}
321 302

  
322 303
/**
......
328 309
 * @return a BOM reading from robot source to robot dest,
329 310
 * in the range 0-15, or -1 if it is unknown
330 311
 **/
331
int wl_token_get_sensor_reading(int source, int dest)
332
{
333
	if (wl_token_is_robot_in_ring(dest) &&
334
			(source == wl_get_xbee_id() || wl_token_is_robot_in_ring(source)))
335
		return sensor_matrix_get_reading(sensorMatrix, source, dest);
336
	return -1;
312
int wl_token_get_sensor_reading(int source, int dest) {
313
  if (wl_token_is_robot_in_ring(dest) &&
314
      (source == wl_get_xbee_id() || wl_token_is_robot_in_ring(source)))
315
    return sensor_matrix_get_reading(sensorMatrix, source, dest);
316
  return -1;
337 317
}
338 318

  
339 319
/**
......
344 324
 * @return a BOM reading from us to robot dest, in the range
345 325
 * 0-15, or -1 if it is unkown
346 326
 **/
347
int wl_token_get_my_sensor_reading(int dest)
348
{
349
	return wl_token_get_sensor_reading(wl_get_xbee_id(), dest);
327
int wl_token_get_my_sensor_reading(int dest) {
328
  return wl_token_get_sensor_reading(wl_get_xbee_id(), dest);
350 329
}
351 330

  
352 331
/**
......
357 336
 *		reading for that robot, repeated for sensorDataLength bytes
358 337
 * @param sensorDataLength the length in bytes of sensorData
359 338
 */
360
void wl_token_pass_receive(int source, char nextRobot, unsigned char* sensorData, int sensorDataLength)
361
{
362
	int i, j;
339
void wl_token_pass_receive(int source, char nextRobot, unsigned char* sensorData, int sensorDataLength) {
340
  int i, j;
363 341

  
364
	// this prevents two tokens from being passed around at a time (second clause is in case we are joining)
365
	if (source != wl_token_next_robot && bom_on_count <= DEATH_DELAY / 2 &&
366
		ringState != ACCEPTED)
367
	{
368
		WL_DEBUG_PRINT("Received token pass when a robot should not have died yet.\n");
369
		WL_DEBUG_PRINT("There are probably two tokens going around, packet ignored.\n");
370
		return;
371
	}
342
  // this prevents two tokens from being passed around at a time (second clause is in case we are joining)
343
  if (source != wl_token_next_robot && bom_on_count <= DEATH_DELAY / 2 &&
344
      ringState != ACCEPTED) {
345
    WL_DEBUG_PRINT("Received token pass when a robot should not have died yet.\n");
346
    WL_DEBUG_PRINT("There are probably two tokens going around, packet ignored.\n");
347
    return;
348
  }
372 349

  
373
	bom_on_count = -1;
374
	deathDelay = -1;
375
	WL_DEBUG_PRINT("Received the token from robot");
376
	WL_DEBUG_PRINT_INT(source);
377
	WL_DEBUG_PRINT(", next robot is ");
378
	WL_DEBUG_PRINT_INT((int)nextRobot);
379
	WL_DEBUG_PRINT(" \r\n");
380
	sensor_matrix_set_in_ring(sensorMatrix, source, 1);
350
  bom_on_count = -1;
351
  deathDelay = -1;
352
  WL_DEBUG_PRINT("Received the token from robot");
353
  WL_DEBUG_PRINT_INT(source);
354
  WL_DEBUG_PRINT(", next robot is ");
355
  WL_DEBUG_PRINT_INT((int)nextRobot);
356
  WL_DEBUG_PRINT(" \r\n");
357
  sensor_matrix_set_in_ring(sensorMatrix, source, 1);
381 358

  
382
	//with this packet, we are passed the id of the next robot in the ring
383
	//and the sensor matrix, a list of id and sensor reading pairs (two bytes for both)
384
	j = 0;
385
	for (i = 0; i < sensor_matrix_get_size(sensorMatrix); i++)
386
	{
387
		if (i == source)
388
			continue;
359
  //with this packet, we are passed the id of the next robot in the ring
360
  //and the sensor matrix, a list of id and sensor reading pairs (two bytes for both)
361
  j = 0;
362
  for (i = 0; i < sensor_matrix_get_size(sensorMatrix); i++) {
363
    if (i == source)
364
      continue;
389 365
		
390
		//set the sensor information we receive
391
		if (j < sensorDataLength / 2 && sensorData[2 * j] == i)
392
		{
393
			//the robot we were going to accept has already been accepted
394
			if (accepted == i)
395
			{
396
				accepted = -1;
397
				WL_DEBUG_PRINT("Someone accepted the robot we did.\r\n");
398
			}
399
			sensor_matrix_set_reading(sensorMatrix, source, i,
400
						sensorData[2 * j + 1]);
401
			sensor_matrix_set_in_ring(sensorMatrix, i, 1);
402
			j++;
403
		}
404
		else
405
		{
406
			if (sensor_matrix_get_in_ring(sensorMatrix, i))
407
			{
408
				WL_DEBUG_PRINT("Robot ");
409
				WL_DEBUG_PRINT_INT(i);
410
				WL_DEBUG_PRINT(" has been removed from the sensor matrix of robot ");
411
				WL_DEBUG_PRINT_INT(wl_get_xbee_id());
412
				WL_DEBUG_PRINT(" due to a packet from robot ");
413
				WL_DEBUG_PRINT_INT(source);
414
				WL_DEBUG_PRINT(".\r\n");
415
				sensor_matrix_set_in_ring(sensorMatrix, i, 0);
416
			}
366
    //set the sensor information we receive
367
    if (j < sensorDataLength / 2 && sensorData[2 * j] == i) {
368
      //the robot we were going to accept has already been accepted
369
      if (accepted == i) {
370
	accepted = -1;
371
	WL_DEBUG_PRINT("Someone accepted the robot we did.\r\n");
372
      }
373
      sensor_matrix_set_reading(sensorMatrix, source, i,
374
				sensorData[2 * j + 1]);
375
      sensor_matrix_set_in_ring(sensorMatrix, i, 1);
376
      j++;
377
    } else {
378
      if (sensor_matrix_get_in_ring(sensorMatrix, i)) {
379
	WL_DEBUG_PRINT("Robot ");
380
	WL_DEBUG_PRINT_INT(i);
381
	WL_DEBUG_PRINT(" has been removed from the sensor matrix of robot ");
382
	WL_DEBUG_PRINT_INT(wl_get_xbee_id());
383
	WL_DEBUG_PRINT(" due to a packet from robot ");
384
	WL_DEBUG_PRINT_INT(source);
385
	WL_DEBUG_PRINT(".\r\n");
386
	sensor_matrix_set_in_ring(sensorMatrix, i, 0);
387
      }
417 388

  
418
			if (i == wl_get_xbee_id() && ringState == MEMBER)
419
			{
420
				ringState = NONMEMBER;
421
				wl_token_ring_join();
389
      if (i == wl_get_xbee_id() && ringState == MEMBER) {
390
	ringState = NONMEMBER;
391
	wl_token_ring_join();
422 392
				
423
				WL_DEBUG_PRINT("We have been removed from the ring ");
424
				WL_DEBUG_PRINT("and are rejoining.\r\n");
425
			}
393
	WL_DEBUG_PRINT("We have been removed from the ring ");
394
	WL_DEBUG_PRINT("and are rejoining.\r\n");
395
      }
426 396
			
427
			//the person who accepted us is dead... let's ask again
428
			if (i == acceptor)
429
			{
430
				sensor_matrix_set_in_ring(sensorMatrix,
431
						wl_get_xbee_id(), 1);
432
				ringState = NONMEMBER;
433
				acceptor = -1;
434
				wl_token_ring_join();
435
			}
436
		}
437
	}
397
      //the person who accepted us is dead... let's ask again
398
      if (i == acceptor) {
399
	sensor_matrix_set_in_ring(sensorMatrix,
400
				  wl_get_xbee_id(), 1);
401
	ringState = NONMEMBER;
402
	acceptor = -1;
403
	wl_token_ring_join();
404
      }
405
    }
406
  }
438 407

  
439
	wl_token_next_robot = nextRobot;
408
  wl_token_next_robot = nextRobot;
440 409
	
441
	deathDelay = get_token_distance(wl_get_xbee_id(), nextRobot) * DEATH_DELAY;
410
  deathDelay = get_token_distance(wl_get_xbee_id(), nextRobot) * DEATH_DELAY;
442 411
	
443
	//we have the token
444
	if (wl_token_next_robot == wl_get_xbee_id())
445
		wl_token_get_token();
412
  //we have the token
413
  if (wl_token_next_robot == wl_get_xbee_id())
414
    wl_token_get_token();
446 415
}
447 416

  
448 417
/**
......
454 423
 * @return the number of passes before the token is expected
455 424
 * to reach robot2 from robot1
456 425
 **/
457
int get_token_distance(int robot1, int robot2)
458
{
459
	int curr = robot1 + 1;
460
	int count = 1;
461
	while (1)
462
	{
463
		if (curr == sensor_matrix_get_size(sensorMatrix))
464
			curr = 0;
465
		if (curr == robot2)
466
			break;
467
		if (sensor_matrix_get_in_ring(sensorMatrix, curr))
468
			count++;
469
		curr++;
470
	}
471
	return count;
426
int get_token_distance(int robot1, int robot2) {
427
  int curr = robot1 + 1;
428
  int count = 1;
429
  while (1) {
430
    if (curr == sensor_matrix_get_size(sensorMatrix))
431
      curr = 0;
432
    if (curr == robot2)
433
      break;
434
    if (sensor_matrix_get_in_ring(sensorMatrix, curr))
435
      count++;
436
    curr++;
437
  }
438
  return count;
472 439
}
473 440

  
474 441
/**
475 442
 * Passes the token to the next robot in the token ring.
476 443
 **/
477
void wl_token_pass_token()
478
{
479
	char nextRobot;
480
	int i = wl_get_xbee_id() + 1;
481
	if (accepted == -1)
482
	{
483
		while (1)
484
		{
485
			if (i == sensor_matrix_get_size(sensorMatrix))
486
				i = 0;
487
			if (sensor_matrix_get_in_ring(sensorMatrix, i))
488
			{
489
				nextRobot = (char)i;
490
				break;
491
			}
492
			i++;
493
		}
494
	}
495
	else
496
	{
497
		WL_DEBUG_PRINT("Accepting new robot, sending it the token.\r\n");
498
		//add a new robot to the token ring
499
		sensor_matrix_set_in_ring(sensorMatrix, accepted, 1);
500
		nextRobot = accepted;
501
		accepted = -1;
502
	}
444
void wl_token_pass_token() {
445
  char nextRobot;
446
  int i = wl_get_xbee_id() + 1;
447
  if (accepted == -1) {
448
    while (1) {
449
      if (i == sensor_matrix_get_size(sensorMatrix))
450
	i = 0;
451
      if (sensor_matrix_get_in_ring(sensorMatrix, i)) {
452
	nextRobot = (char)i;
453
	break;
454
      }
455
      i++;
456
    }
457
  } else {
458
    WL_DEBUG_PRINT("Accepting new robot, sending it the token.\r\n");
459
    //add a new robot to the token ring
460
    sensor_matrix_set_in_ring(sensorMatrix, accepted, 1);
461
    nextRobot = accepted;
462
    accepted = -1;
463
  }
503 464

  
504
	//we don't include ourself
505
	int packetSize = 1 + 2 * (sensor_matrix_get_joined(sensorMatrix) - 1);
506
	char* buf = (char*)malloc(packetSize * sizeof(char));
507
	if (!buf)
508
	{
509
		WL_DEBUG_PRINT_INT(packetSize);
510
		WL_DEBUG_PRINT("Out of memory - pass token.\r\n");
511
		return;
512
	}
513
	buf[0] = nextRobot;
465
  //we don't include ourself
466
  int packetSize = 1 + 2 * (sensor_matrix_get_joined(sensorMatrix) - 1);
467
  char* buf = (char*)malloc(packetSize * sizeof(char));
468
  if (!buf) {
469
    WL_DEBUG_PRINT_INT(packetSize);
470
    WL_DEBUG_PRINT("Out of memory - pass token.\r\n");
471
    return;
472
  }
473
  buf[0] = nextRobot;
514 474

  
515
	int j = 0;
516
	for (i = 0; i < sensor_matrix_get_size(sensorMatrix); i++)
517
		if (sensor_matrix_get_in_ring(sensorMatrix, i) && i != wl_get_xbee_id())
518
		{
519
			buf[2*j + 1] = i;
520
			buf[2*j + 2] = sensor_matrix_get_reading(sensorMatrix, wl_get_xbee_id(), i);
521
			j++;
522
		}
475
  int j = 0;
476
  for (i = 0; i < sensor_matrix_get_size(sensorMatrix); i++)
477
    if (sensor_matrix_get_in_ring(sensorMatrix, i) && i != wl_get_xbee_id()) {
478
      buf[2*j + 1] = i;
479
      buf[2*j + 2] = sensor_matrix_get_reading(sensorMatrix, wl_get_xbee_id(), i);
480
      j++;
481
    }
523 482
	
524
	WL_DEBUG_PRINT("Passing the token to robot ");
525
	WL_DEBUG_PRINT_INT(buf[0]);
526
	WL_DEBUG_PRINT(".\r\n");
527
	wl_send_global_packet(WL_TOKEN_RING_GROUP, WL_TOKEN_PASS,
528
		buf, packetSize, 3);
483
  WL_DEBUG_PRINT("Passing the token to robot ");
484
  WL_DEBUG_PRINT_INT(buf[0]);
485
  WL_DEBUG_PRINT(".\r\n");
486
  wl_send_global_packet(WL_TOKEN_RING_GROUP, WL_TOKEN_PASS,
487
			buf, packetSize, 3);
529 488

  
530
	wl_token_next_robot = nextRobot;
531
	deathDelay = DEATH_DELAY;
532
	free(buf);
489
  wl_token_next_robot = nextRobot;
490
  deathDelay = DEATH_DELAY;
491
  free(buf);
533 492
}
534 493

  
535 494
/**
......
539 498
 *
540 499
 * @param source the robot whose BOM is on
541 500
 **/
542
void wl_token_bom_on_receive(int source)
543
{
544
	WL_DEBUG_PRINT("Robot ");
545
	WL_DEBUG_PRINT_INT(source);
546
	WL_DEBUG_PRINT(" has flashed its bom.\r\n");
501
void wl_token_bom_on_receive(int source) {
502
  WL_DEBUG_PRINT("Robot ");
503
  WL_DEBUG_PRINT_INT(source);
504
  WL_DEBUG_PRINT(" has flashed its bom.\r\n");
547 505
	
548
	bom_on_count = 0;
506
  bom_on_count = 0;
549 507

  
550
	sensor_matrix_set_reading(sensorMatrix, wl_get_xbee_id(), 
551
		source, get_max_bom_function());
508
  sensor_matrix_set_reading(sensorMatrix, wl_get_xbee_id(), 
509
			    source, get_max_bom_function());
552 510
}
553 511

  
554 512
/**
......
558 516
 * 
559 517
 * If there is a pending request for the token, this is processed first.
560 518
 **/
561
void wl_token_get_token()
562
{
563
	WL_DEBUG_PRINT("We have the token.\r\n");
564
	if (ringState == ACCEPTED)
565
	{
566
		sensor_matrix_set_in_ring(sensorMatrix,
567
			wl_get_xbee_id(), 1);
568
		WL_DEBUG_PRINT("Now a member of the token ring.\r\n");
569
		ringState = MEMBER;
570
		joinDelay = -1;
571
	}
519
void wl_token_get_token() {
520
  WL_DEBUG_PRINT("We have the token.\r\n");
521
  if (ringState == ACCEPTED) {
522
    sensor_matrix_set_in_ring(sensorMatrix,
523
			      wl_get_xbee_id(), 1);
524
    WL_DEBUG_PRINT("Now a member of the token ring.\r\n");
525
    ringState = MEMBER;
526
    joinDelay = -1;
527
  }
572 528

  
573
	if (ringState == LEAVING || ringState == NONMEMBER)
574
	{
575
		sensor_matrix_set_in_ring(sensorMatrix, wl_get_xbee_id(), 0);
576
		if (ringState == NONMEMBER)
577
		{
578
			WL_DEBUG_PRINT("We should have left the token ring, but didn't.\r\n");
579
		}
580
		return;
581
	}
529
  if (ringState == LEAVING || ringState == NONMEMBER) {
530
    sensor_matrix_set_in_ring(sensorMatrix, wl_get_xbee_id(), 0);
531
    if (ringState == NONMEMBER) {
532
      WL_DEBUG_PRINT("We should have left the token ring, but didn't.\r\n");
533
    }
534
    return;
535
  }
582 536
	
583
	WL_DEBUG_PRINT("Our BOM has been flashed.\r\n");
584
	wl_send_global_packet(WL_TOKEN_RING_GROUP, WL_TOKEN_BOM_ON,
585
		NULL, 0, 0);
537
  WL_DEBUG_PRINT("Our BOM has been flashed.\r\n");
538
  wl_send_global_packet(WL_TOKEN_RING_GROUP, WL_TOKEN_BOM_ON,
539
			NULL, 0, 0);
586 540

  
587
	bom_on_function();
588
	#ifdef ROBOT
589
	delay_ms(BOM_DELAY);
590
	#endif
591
	bom_off_function();
541
  bom_on_function();
542
#ifdef ROBOT
543
  delay_ms(BOM_DELAY);
544
#endif
545
  bom_off_function();
592 546
	
593
	if (!sensor_matrix_get_in_ring(sensorMatrix, wl_get_xbee_id()))
594
	{
595
		WL_DEBUG_PRINT("Removed from sensor matrix while flashing BOM.\r\n");
596
		return;
597
	}
547
  if (!sensor_matrix_get_in_ring(sensorMatrix, wl_get_xbee_id())) {
548
    WL_DEBUG_PRINT("Removed from sensor matrix while flashing BOM.\r\n");
549
    return;
550
  }
598 551
	
599
	wl_token_pass_token();
552
  wl_token_pass_token();
600 553
}
601 554

  
602 555
/**
......
607 560
 *
608 561
 * @param source the robot who requested to join
609 562
 **/
610
void wl_token_join_receive(int source)
611
{
612
	WL_DEBUG_PRINT("Received joining request from robot ");
613
	WL_DEBUG_PRINT_INT(source);
614
	WL_DEBUG_PRINT(".\r\n");
563
void wl_token_join_receive(int source) {
564
  WL_DEBUG_PRINT("Received joining request from robot ");
565
  WL_DEBUG_PRINT_INT(source);
566
  WL_DEBUG_PRINT(".\r\n");
615 567

  
616
	//we cannot accept the request if we are not a member
617
	if (ringState != MEMBER)
618
		return;
619
	//if they didn't get our response, see if we should respond again
620
	if (accepted == source)
621
		accepted = -1;
622
	//we can only accept one request at a time
623
	if (accepted != -1)
624
		return;
568
  //we cannot accept the request if we are not a member
569
  if (ringState != MEMBER)
570
    return;
571
  //if they didn't get our response, see if we should respond again
572
  if (accepted == source)
573
    accepted = -1;
574
  //we can only accept one request at a time
575
  if (accepted != -1)
576
    return;
625 577
	
626
	//check if we are the preceding robot in the token ring
627
	int i = source - 1;
628
	while (1)
629
	{
630
		if (i < 0)
631
			i = sensor_matrix_get_size(sensorMatrix) - 1;
632
		//we must send a join acceptance
633
		if (i == wl_get_xbee_id())
634
			break;
578
  //check if we are the preceding robot in the token ring
579
  int i = source - 1;
580
  while (1) {
581
    if (i < 0)
582
      i = sensor_matrix_get_size(sensorMatrix) - 1;
583
    //we must send a join acceptance
584
    if (i == wl_get_xbee_id())
585
      break;
635 586

  
636
		//another robot will handle it
637
		if (sensor_matrix_get_in_ring(sensorMatrix, i))
638
			return;
639
		i--;
640
	}
587
    //another robot will handle it
588
    if (sensor_matrix_get_in_ring(sensorMatrix, i))
589
      return;
590
    i--;
591
  }
641 592

  
642
	accepted = source;
643
	wl_send_robot_to_robot_global_packet(WL_TOKEN_RING_GROUP, WL_TOKEN_JOIN_ACCEPT,
644
		NULL, 0, source, TOKEN_JOIN_ACCEPT_FRAME);
593
  accepted = source;
594
  wl_send_robot_to_robot_global_packet(WL_TOKEN_RING_GROUP, WL_TOKEN_JOIN_ACCEPT,
595
				       NULL, 0, source, TOKEN_JOIN_ACCEPT_FRAME);
645 596
	
646
	WL_DEBUG_PRINT("Accepting robot ");
647
	WL_DEBUG_PRINT_INT(source);
648
	WL_DEBUG_PRINT(" into the token ring.\r\n");
597
  WL_DEBUG_PRINT("Accepting robot ");
598
  WL_DEBUG_PRINT_INT(source);
599
  WL_DEBUG_PRINT(" into the token ring.\r\n");
649 600

  
650
	// the token ring has not started yet
651
	if (sensor_matrix_get_joined(sensorMatrix) == 1)
652
		wl_token_pass_token();
601
  // the token ring has not started yet
602
  if (sensor_matrix_get_joined(sensorMatrix) == 1)
603
    wl_token_pass_token();
653 604
}
654 605

  
655 606
/**
......
659 610
 *
660 611
 * @param source the robot who accepted us
661 612
 **/
662
void wl_token_join_accept_receive(int source)
663
{
664
	WL_DEBUG_PRINT("Accepted into the token ring by robot ");
665
	WL_DEBUG_PRINT_INT(source);
666
	WL_DEBUG_PRINT(".\r\n");
667
	joinDelay = JOIN_DELAY;
668
	ringState = ACCEPTED;
669
	acceptor = source;
613
void wl_token_join_accept_receive(int source) {
614
  WL_DEBUG_PRINT("Accepted into the token ring by robot ");
615
  WL_DEBUG_PRINT_INT(source);
616
  WL_DEBUG_PRINT(".\r\n");
617
  joinDelay = JOIN_DELAY;
618
  ringState = ACCEPTED;
619
  acceptor = source;
670 620

  
671
	//add ourselves to the token ring
672
	sensor_matrix_set_in_ring(sensorMatrix, wl_get_xbee_id(), 1);
621
  //add ourselves to the token ring
622
  sensor_matrix_set_in_ring(sensorMatrix, wl_get_xbee_id(), 1);
673 623
}
674 624

  
675 625
/**
......
677 627
 *
678 628
 * @return the number of robots in the token ring
679 629
 **/
680
int wl_token_get_robots_in_ring(void)
681
{
682
	return sensor_matrix_get_joined(sensorMatrix);
630
int wl_token_get_robots_in_ring(void) {
631
  return sensor_matrix_get_joined(sensorMatrix);
683 632
}
684 633

  
685 634
/**
......
689 638
 * @param robot the robot to check for whether it is in the token ring
690 639
 * @return nonzero if the robot is in the token ring, zero otherwise
691 640
 **/
692
int wl_token_is_robot_in_ring(int robot)
693
{
694
	return sensor_matrix_get_in_ring(sensorMatrix, robot);
641
int wl_token_is_robot_in_ring(int robot) {
642
  return sensor_matrix_get_in_ring(sensorMatrix, robot);
695 643
}
696 644

  
697 645
/**
......
699 647
 *
700 648
 * @see wl_token_iterator_has_next, wl_token_iterator_next
701 649
 **/
702
void wl_token_iterator_begin(void)
703
{
704
	int i = 0;
705
	iteratorCount = 0;
706
	while (!sensor_matrix_get_in_ring(sensorMatrix, i) &&
707
			i < sensor_matrix_get_size(sensorMatrix))
708
		i++;
709
	if (i == sensor_matrix_get_size(sensorMatrix))
710
		i = -1;
711
	iteratorCount = i;
650
void wl_token_iterator_begin(void) {
651
  int i = 0;
652
  iteratorCount = 0;
653
  while (!sensor_matrix_get_in_ring(sensorMatrix, i) &&
654
	 i < sensor_matrix_get_size(sensorMatrix))
655
    i++;
656
  if (i == sensor_matrix_get_size(sensorMatrix))
657
    i = -1;
658
  iteratorCount = i;
712 659
}
713 660

  
714 661
/**
......
720 667
 *
721 668
 * @see wl_token_iterator_begin, wl_token_iterator_next
722 669
 **/
723
int wl_token_iterator_has_next(void)
724
{
725
	return iteratorCount != -1;
670
int wl_token_iterator_has_next(void) {
671
  return iteratorCount != -1;
726 672
}
727 673

  
728 674
/**
......
732 678
 *
733 679
 * @see wl_token_iterator_begin, wl_token_iterator_has_next
734 680
 **/
735
int wl_token_iterator_next(void)
736
{
737
	int result = iteratorCount;
738
	if (result < 0)
739
		return result;
681
int wl_token_iterator_next(void) {
682
  int result = iteratorCount;
683
  if (result < 0)
684
    return result;
740 685

  
741
	iteratorCount++;
742
	while (!sensor_matrix_get_in_ring(sensorMatrix, iteratorCount) &&
743
		iteratorCount < sensor_matrix_get_size(sensorMatrix))
744
		iteratorCount++;
745
	if (iteratorCount == sensor_matrix_get_size(sensorMatrix))
746
		iteratorCount = -1;
747
	return result;
686
  iteratorCount++;
687
  while (!sensor_matrix_get_in_ring(sensorMatrix, iteratorCount) &&
688
	 iteratorCount < sensor_matrix_get_size(sensorMatrix))
689
    iteratorCount++;
690
  if (iteratorCount == sensor_matrix_get_size(sensorMatrix))
691
    iteratorCount = -1;
692
  return result;
748 693
}
749 694

  
750 695
/**
......
752 697
 *
753 698
 * @return the number of robots in the token ring
754 699
 **/
755
int wl_token_get_num_robots(void)
756
{
757
	return sensor_matrix_get_joined(sensorMatrix);
700
int wl_token_get_num_robots(void) {
701
  return sensor_matrix_get_joined(sensorMatrix);
758 702
}
759 703

  
760 704
/**
......
762 706
 *
763 707
 * @return the number of robots in the sensor matrix
764 708
 **/
765
int wl_token_get_matrix_size(void)
766
{
767
	return sensor_matrix_get_size(sensorMatrix);
709
int wl_token_get_matrix_size(void) {
710
  return sensor_matrix_get_size(sensorMatrix);
768 711
}
769

  
trunk/code/projects/libwireless/lib/sensor_matrix.h
51 51
 *
52 52
 * A sensor matrix.
53 53
 **/
54
typedef struct
55
{
56
	/**
57
	 * The size of the sensor matrix.
58
	**/
59
	int size;
60
	/**
61
	 * The matrix. Each row represents the readings of one
62
	 * robot.
63
	 **/
64
	int** matrix;
65
	/**
66
	 * The element representing a robot is true if that robot
67
	 * is in the token ring and false otherwise.
68
	 **/
69
	int* joined;
70
	/**
71
	 * The number of robots in the token ring.
72
	 **/
73
	int numJoined;
54
typedef struct {
55
  /**
56
   * The size of the sensor matrix.
57
   **/
58
  int size;
59
  /**
60
   * The matrix. Each row represents the readings of one
61
   * robot.
62
   **/
63
  int** matrix;
64
  /**
65
   * The element representing a robot is true if that robot
66
   * is in the token ring and false otherwise.
67
   **/
68
  int* joined;
69
  /**
70
   * The number of robots in the token ring.
71
   **/
72
  int numJoined;
74 73
} SensorMatrix;
75 74

  
76 75
/**@brief Create a sensor matrix **/
trunk/code/projects/libwireless/lib/wireless.h
72 72
 * handlers for various events which can occur related to a packet
73 73
 * group.
74 74
 **/
75
typedef struct
76
{
75
typedef struct {
77 76
	/**
78 77
	 * The group code for this packet group. This number
79 78
	 * must be unique. The maximum number of packet groups
trunk/code/projects/libwireless/lib/xbee.c
90 90

  
91 91
int xbee_handle_packet(char* packet, int len);
92 92
void xbee_handle_at_command_response(char* command, char result,
93
	char* extra, int extraLen);
93
				     char* extra, int extraLen);
94 94
void xbee_handle_status(char status);
95 95
int xbee_verify_checksum(char* packet, int len);
96 96
char xbee_compute_checksum(char* packet, int len);
......
136 136
 * to the buffer.
137 137
 **/
138 138
#ifndef FIREFLY
139
ISR(USART1_RX_vect)
140
{
141
	char c = UDR1;
142
	arrival_buf[buffer_last] = c;
143
	int t = buffer_last + 1;
144
	if (t == XBEE_BUFFER_SIZE)
145
		t = 0;
146
	if (t == buffer_first)
147
	{
148
		WL_DEBUG_PRINT("Out of space in buffer.\n");
149
	}
150
	buffer_last = t;
139
ISR(USART1_RX_vect) {
140
  char c = UDR1;
141
  arrival_buf[buffer_last] = c;
142
  int t = buffer_last + 1;
143
  if (t == XBEE_BUFFER_SIZE)
144
    t = 0;
145
  if (t == buffer_first) {
146
    WL_DEBUG_PRINT("Out of space in buffer.\n");
147
  }
148
  buffer_last = t;
151 149
}
152 150
#else
153
SIGNAL(SIG_USART0_RECV)
154
{
155
	char c = UDR0;
156
	arrival_buf[buffer_last] = c;
157
	int t = buffer_last + 1;
158
	if (t == XBEE_BUFFER_SIZE)
159
		t = 0;
160
	if (t == buffer_first)
161
	{
162
		WL_DEBUG_PRINT("Out of space in buffer.\n");
163
	}
164
	buffer_last = t;
151
SIGNAL(SIG_USART0_RECV) {
152
  char c = UDR0;
153
  arrival_buf[buffer_last] = c;
154
  int t = buffer_last + 1;
155
  if (t == XBEE_BUFFER_SIZE)
156
    t = 0;
157
  if (t == buffer_first) {
158
    WL_DEBUG_PRINT("Out of space in buffer.\n");
159
  }
160
  buffer_last = t;
165 161
}
166 162
#endif
167 163

  
......
170 166
/**
171 167
 * Thread that listens to the xbee.
172 168
 **/
173
void* listen_to_xbee(void* x)
174
{
175
	char c;
176
	while (1)
177
	{
178
		xbee_read(&c, 1);
179
		arrival_buf[buffer_last] = c;
180
		int t = buffer_last + 1;
181
		if (t == XBEE_BUFFER_SIZE)
182
			t = 0;
183
		if (t == buffer_first)
184
		{
185
			WL_DEBUG_PRINT("Out of space in buffer.\n");
186
		}
187
		buffer_last = t;
188
	}
189
	return 0;
169
void* listen_to_xbee(void* x) {
170
  char c;
171
  while (1) {
172
    xbee_read(&c, 1);
173
    arrival_buf[buffer_last] = c;
174
    int t = buffer_last + 1;
175
    if (t == XBEE_BUFFER_SIZE)
176
      t = 0;
177
    if (t == buffer_first) {
178
      WL_DEBUG_PRINT("Out of space in buffer.\n");
179
    }
180
    buffer_last = t;
181
  }
182
  return 0;
190 183
}
191 184

  
192 185
#endif
......
194 187
/**
195 188
 * Initializes the XBee library so that other functions may be used.
196 189
 **/
197
int xbee_lib_init(void)
198
{
199
	arrival_buf[0] = 'A';
200
	arrival_buf[1] = 'A';
201
	arrival_buf[2] = 'A';
202
	#ifdef ROBOT
190
int xbee_lib_init(void) {
191
  arrival_buf[0] = 'A';
192
  arrival_buf[1] = 'A';
193
  arrival_buf[2] = 'A';
194
#ifdef ROBOT
203 195

  
204
	//enable the receiving interrupt
205
	#ifdef FIREFLY
206
	UCSR0B |= _BV(RXCIE) | _BV(RXEN);
207
	#else
208
	UCSR1B |= _BV(RXCIE);
209
	#endif
210
	sei();
211
	#else
212
	printf("Connecting to port %s.\n", xbee_com_port);
213
	xbee_stream = open(xbee_com_port, O_RDWR);
214
	if (xbee_stream == -1/* || lockf(xbee_stream, F_TEST, 0) != 0*/)
215
	{
216
		printf("Failed to open connection to XBee on port %s\r\n", xbee_com_port);
217
		return -1;
218
	}
196
  //enable the receiving interrupt
197
#ifdef FIREFLY
198
  UCSR0B |= _BV(RXCIE) | _BV(RXEN);
199
#else
200
  UCSR1B |= _BV(RXCIE);
201
#endif
202
  sei();
203
#else
204
  printf("Connecting to port %s.\n", xbee_com_port);
205
  xbee_stream = open(xbee_com_port, O_RDWR);
206
  if (xbee_stream == -1/* || lockf(xbee_stream, F_TEST, 0) != 0*/) {
207
    printf("Failed to open connection to XBee on port %s\r\n", xbee_com_port);
208
    return -1;
209
  }
219 210
	
220
	// set baud rate, etc. correctly
221
	struct termios options;
211
  // set baud rate, etc. correctly
212
  struct termios options;
222 213

  
223
	tcgetattr(xbee_stream, &options);
224
	cfsetispeed(&options, B9600);
225
	cfsetospeed(&options, B9600);
226
	options.c_iflag &= ~ICRNL;
227
	options.c_oflag &= ~OCRNL;
228
	options.c_cflag |= (CLOCAL | CREAD);
229
	options.c_cflag &= ~PARENB;
230
	options.c_cflag &= ~CSTOPB;
231
	options.c_cflag &= ~CSIZE;
232
	options.c_cflag |= CS8;
233
	options.c_lflag &= ~ICANON;
234
	options.c_cc[VMIN] = 1;
235
	options.c_cc[VTIME] = 50;
214
  tcgetattr(xbee_stream, &options);
215
  cfsetispeed(&options, B9600);
216
  cfsetospeed(&options, B9600);
217
  options.c_iflag &= ~ICRNL;
218
  options.c_oflag &= ~OCRNL;
219
  options.c_cflag |= (CLOCAL | CREAD);
220
  options.c_cflag &= ~PARENB;
221
  options.c_cflag &= ~CSTOPB;
222
  options.c_cflag &= ~CSIZE;
223
  options.c_cflag |= CS8;
224
  options.c_lflag &= ~ICANON;
225
  options.c_cc[VMIN] = 1;
226
  options.c_cc[VTIME] = 50;
236 227

  
237
	if (tcsetattr(xbee_stream, TCSANOW, &options))
238
	{
239
		fprintf(stderr, "Error setting attributes.\n");
240
		return -1;
241
	}
228
  if (tcsetattr(xbee_stream, TCSANOW, &options)) {
229
    fprintf(stderr, "Error setting attributes.\n");
230
    return -1;
231
  }
242 232

  
243
	//lockf(xbee_stream, F_LOCK, 0);
233
  //lockf(xbee_stream, F_LOCK, 0);
244 234
	
245
	xbee_listen_thread =
246
		(pthread_t*)malloc(sizeof(pthread_t));
247
	if (xbee_listen_thread == NULL)
248
	{
249
		fprintf(stderr, "%s: Malloc failed.\n", __FUNCTION__);
250
		return -1;
251
	}
235
  xbee_listen_thread =
236
    (pthread_t*)malloc(sizeof(pthread_t));
237
  if (xbee_listen_thread == NULL) {
238
    fprintf(stderr, "%s: Malloc failed.\n", __FUNCTION__);
239
    return -1;
240
  }
252 241
	
253
	int ret = pthread_create(xbee_listen_thread, NULL,
254
		listen_to_xbee, NULL);
255
	if (ret)
256
	{
257
		fprintf(stderr, "Failed to create listener thread.\r\n");
258
		return -1;
259
	}
242
  int ret = pthread_create(xbee_listen_thread, NULL,
243
			   listen_to_xbee, NULL);
244
  if (ret) {
245
    fprintf(stderr, "Failed to create listener thread.\r\n");
246
    return -1;
247
  }
260 248
	
261
	#endif
262
	xbee_enter_command_mode();
263
	xbee_enter_api_mode();
264
	xbee_exit_command_mode();
265
	xbee_send_read_at_command("MY");
249
#endif
250
  xbee_enter_command_mode();
251
  xbee_enter_api_mode();
252
  xbee_exit_command_mode();
253
  xbee_send_read_at_command("MY");
266 254
	
267
	//wait to return until the address is set
268
	while (xbee_address == 0) xbee_get_packet(NULL);
255
  //wait to return until the address is set
256
  while (xbee_address == 0) xbee_get_packet(NULL);
269 257

  
270

  
271
	return 0;
258
  return 0;
272 259
}
273 260

  
274 261
/**
275 262
 * Call when finished using the XBee library. This releases
276 263
 * all sued resources.
277 264
 **/
278
void xbee_terminate()
279
{
280
	#ifndef ROBOT
281
	pthread_cancel(*xbee_listen_thread);
282
	free(xbee_listen_thread);
283
	lockf(xbee_stream, F_ULOCK, 0);
284
	close(xbee_stream);
285
	#endif
265
void xbee_terminate() {
266
#ifndef ROBOT
267
  pthread_cancel(*xbee_listen_thread);
268
  free(xbee_listen_thread);
269
  lockf(xbee_stream, F_ULOCK, 0);
270
  close(xbee_stream);
271
#endif
286 272
}
287 273

  
288 274
/**
......
291 277
 * @param buf the buffer of data to send
292 278
 * @param size the number of bytes to send
293 279
 **/
294
void xbee_send(char* buf, int size)
295
{
296
	#ifdef ROBOT
297
	int i;
298
	for (i = 0; i < size; i++)
299
		xbee_putc(buf[i]);
300
	#else
301
	int ret = write(xbee_stream, buf, size);
302
	//success
303
	if (ret == size)
304
		return;
305
	if (ret == -1)
306
	{
307
		//interrupted by system signal, probably timer interrupt.
308
		//just try again
309
		if (errno == 4)
310
		{
311
			xbee_send(buf, size);
312
			return;
313
		}
314
		printf("Failed to write to xbee, error %i.\r\n", errno);
315
		return;
316
	}
280
void xbee_send(char* buf, int size) {
281
#ifdef ROBOT
282
  int i;
283
  for (i = 0; i < size; i++)
284
    xbee_putc(buf[i]);
285
#else
286
  int ret = write(xbee_stream, buf, size);
287
  //success
288
  if (ret == size)
289
    return;
290
  if (ret == -1) {
291
    //interrupted by system signal, probably timer interrupt.
292
    //just try again
293
    if (errno == 4) {
294
      xbee_send(buf, size);
295
      return;
296
    }
297
    printf("Failed to write to xbee, error %i.\r\n", errno);
298
    return;
299
  }
317 300

  
318
	//write was interrupted after writing ret bytes
319
	xbee_send(buf + ret, size - ret);
320
	#endif
301
  //write was interrupted after writing ret bytes
302
  xbee_send(buf + ret, size - ret);
303
#endif
321 304
}
322 305

  
323 306
/**
......
325 308
 *
326 309
 * @param c the string to send to the XBEE
327 310
 **/
328
void xbee_send_string(char* c)
329
{
330
	xbee_send(c, strlen(c));
311
void xbee_send_string(char* c) {
312
  xbee_send(c, strlen(c));
331 313
}
332 314

  
333 315
#ifndef ROBOT
334
void xbee_read(char* buf, int size)
335
{
336
	if (read(xbee_stream, buf, size) == -1)
337
		printf("Failed to read from xbee.\r\n");
316
void xbee_read(char* buf, int size) {
317
  if (read(xbee_stream, buf, size) == -1)
318
    printf("Failed to read from xbee.\r\n");
338 319
}
339 320
#endif
340 321

  
341 322
/**
342 323
 * Enter into command mode.
343 324
 **/
344
void xbee_enter_command_mode()
345
{
346
	xbee_send_string("+++");
347
	xbee_wait_for_ok();
325
void xbee_enter_command_mode() {
326
  xbee_send_string("+++");
327
  xbee_wait_for_ok();
348 328
}
349 329

  
350 330
/**
351 331
 * Exit from command mode.
352 332
 **/
353
void xbee_exit_command_mode()
354
{
355
	xbee_send_string("ATCN\r");
356
	xbee_wait_for_ok();
333
void xbee_exit_command_mode() {
334
  xbee_send_string("ATCN\r");
335
  xbee_wait_for_ok();
357 336
}
358 337

  
359 338
/**
360 339
 * Enter API mode.
361 340
 **/
362
void xbee_enter_api_mode()
363
{
364
	xbee_send_string("ATAP 1\r");
365
	xbee_wait_for_ok();
341
void xbee_enter_api_mode() {
342
  xbee_send_string("ATAP 1\r");
343
  xbee_wait_for_ok();
366 344
}
367 345

  
368 346
/**
369 347
 * Exit API mode. (warning - does not check for response)
370 348
 **/
371
void xbee_exit_api_mode()
372
{
373
	xbee_send_string("ATAP 0\r");
349
void xbee_exit_api_mode() {
350
  xbee_send_string("ATAP 0\r");
374 351
}
375 352

  
376 353
/**
377 354
 * Wait until the string "OK\r" is received from the XBee.
378 355
 **/
379
void xbee_wait_for_ok()
380
{
381
	xbee_wait_for_string("OK\r", 3);
356
void xbee_wait_for_ok() {
357
  xbee_wait_for_string("OK\r", 3);
382 358
}
383 359

  
384 360
/**
......
388 364
 * @param s the string to receive
389 365
 * @param len the length of the string
390 366
 **/
391
void xbee_wait_for_string(char* s, int len)
392
{
393
	char* curr = s;
394
	while (curr - s < len)
395
	{
396
		// check if buffer is empty
397
		if (buffer_last == buffer_first)
398
			continue;
399
		char c = arrival_buf[buffer_first++];
400
		if (buffer_first == XBEE_BUFFER_SIZE)
401
			buffer_first = 0;
402
		if (c == *curr)
403
			curr++;
404
		else
405
			curr = s;
406
	}
367
void xbee_wait_for_string(char* s, int len) {
368
  char* curr = s;
369
  while (curr - s < len) {
370
    // check if buffer is empty
371
    if (buffer_last == buffer_first)
372
      continue;
373
    char c = arrival_buf[buffer_first++];
374
    if (buffer_first == XBEE_BUFFER_SIZE)
375
      buffer_first = 0;
376
    if (c == *curr)
377
      curr++;
378
    else
379
      curr = s;
380
  }
407 381
}
408 382

  
409 383
/**
......
419 393
 * @return 0 if the checksum is incorrect, nonzero
420 394
 * otherwise
421 395
 **/
422
int xbee_verify_checksum(char* packet, int len)
423
{
424
	unsigned char sum = 0;
425
	int i;
426
	for (i = 3; i < len; i++)
427
		sum += (unsigned char)packet[i];
428
	return sum == 0xFF;
396
int xbee_verify_checksum(char* packet, int len) {
397
  unsigned char sum = 0;
398
  int i;
399
  for (i = 3; i < len; i++)
400
    sum += (unsigned char)packet[i];
401
  return sum == 0xFF;
429 402
}
430 403

  
431 404
/**
......
437 410
 * @return the checksum of the packet, which will
438 411
 * become the last byte sent in the packet
439 412
 **/
440
char xbee_compute_checksum(char* buf, int len)
441
{
442
	int i;
443
	unsigned char sum = 0;
444
	for (i = 0; i < len; i++)
445
		sum += (unsigned char)buf[i];
446
	return 0xFF - sum;
413
char xbee_compute_checksum(char* buf, int len) {
414
  int i;
415
  unsigned char sum = 0;
416
  for (i = 0; i < len; i++)
417
    sum += (unsigned char)buf[i];
418
  return 0xFF - sum;
447 419
}
448 420

  
449 421
/**
......
455 427
 * @param len the size in bytes of the packet data
456 428
 *
... This diff was truncated because it exceeds the maximum size that can be displayed.

Also available in: Unified diff