RTEMS CPU Kit with SuperCore  4.11.2
chainimpl.h
Go to the documentation of this file.
1 
7 /*
8  * Copyright (c) 2010 embedded brains GmbH.
9  *
10  * COPYRIGHT (c) 1989-2014.
11  * On-Line Applications Research Corporation (OAR).
12  *
13  * The license and distribution terms for this file may be
14  * found in the file LICENSE in this distribution or at
15  * http://www.rtems.org/license/LICENSE.
16  */
17 
18 #ifndef _RTEMS_SCORE_CHAINIMPL_H
19 #define _RTEMS_SCORE_CHAINIMPL_H
20 
21 #include <rtems/score/chain.h>
22 #include <rtems/score/address.h>
23 #include <rtems/score/assert.h>
24 
25 #ifdef __cplusplus
26 extern "C" {
27 #endif
28 
37 #define CHAIN_INITIALIZER_EMPTY(name) \
38  { { { &(name).Tail.Node, NULL }, &(name).Head.Node } }
39 
45 #define CHAIN_INITIALIZER_ONE_NODE( node ) \
46  { { { (node), NULL }, (node) } }
47 
53 #define CHAIN_NODE_INITIALIZER_ONE_NODE_CHAIN( chain ) \
54  { &(chain)->Tail.Node, &(chain)->Head.Node }
55 
59 #define CHAIN_DEFINE_EMPTY(name) \
60  Chain_Control name = CHAIN_INITIALIZER_EMPTY(name)
61 
76  Chain_Control *the_chain,
77  void *starting_address,
78  size_t number_nodes,
79  size_t node_size
80 );
81 
93 void _Chain_Extract(
94  Chain_Node *the_node
95 );
96 
110  Chain_Control *the_chain
111 );
112 
129 void _Chain_Insert(
130  Chain_Node *after_node,
131  Chain_Node *the_node
132 );
133 
142 void _Chain_Append(
143  Chain_Control *the_chain,
144  Chain_Node *the_node
145 );
146 
162  Chain_Control *the_chain,
163  Chain_Node *the_node
164 );
165 
181  Chain_Control *the_chain,
182  Chain_Node *the_node
183 );
184 
206  Chain_Control *the_chain,
207  Chain_Node **the_node
208 );
209 
220 size_t _Chain_Node_count_unprotected( const Chain_Control *chain );
221 
231  Chain_Node *node
232 )
233 {
234  node->next = NULL;
235 }
236 
249  const Chain_Node *node
250 )
251 {
252  return node->next == NULL;
253 }
254 
268  const Chain_Node *left,
269  const Chain_Node *right
270 )
271 {
272  return left == right;
273 }
274 
286  const Chain_Node *the_node
287 )
288 {
289  return (the_node == NULL);
290 }
291 
302  Chain_Control *the_chain
303 )
304 {
305  return &the_chain->Head.Node;
306 }
307 
318  const Chain_Control *the_chain
319 )
320 {
321  return &the_chain->Head.Node;
322 }
323 
334  Chain_Control *the_chain
335 )
336 {
337  return &the_chain->Tail.Node;
338 }
339 
350  const Chain_Control *the_chain
351 )
352 {
353  return &the_chain->Tail.Node;
354 }
355 
367  Chain_Control *the_chain
368 )
369 {
370  return _Chain_Head( the_chain )->next;
371 }
372 
384  const Chain_Control *the_chain
385 )
386 {
387  return _Chain_Immutable_head( the_chain )->next;
388 }
389 
401  Chain_Control *the_chain
402 )
403 {
404  return _Chain_Tail( the_chain )->previous;
405 }
406 
418  const Chain_Control *the_chain
419 )
420 {
421  return _Chain_Immutable_tail( the_chain )->previous;
422 }
423 
434  Chain_Node *the_node
435 )
436 {
437  return the_node->next;
438 }
439 
450  const Chain_Node *the_node
451 )
452 {
453  return the_node->next;
454 }
455 
466  Chain_Node *the_node
467 )
468 {
469  return the_node->previous;
470 }
471 
482  const Chain_Node *the_node
483 )
484 {
485  return the_node->previous;
486 }
487 
500  const Chain_Control *the_chain
501 )
502 {
503  return _Chain_Immutable_first( the_chain )
504  == _Chain_Immutable_tail( the_chain );
505 }
506 
520  const Chain_Node *the_node
521 )
522 {
523  return (the_node->previous->previous == NULL);
524 }
525 
538  const Chain_Node *the_node
539 )
540 {
541  return (the_node->next->next == NULL);
542 }
543 
559  const Chain_Control *the_chain
560 )
561 {
562  return _Chain_Immutable_first( the_chain )
563  == _Chain_Immutable_last( the_chain );
564 }
565 
579  const Chain_Control *the_chain,
580  const Chain_Node *the_node
581 )
582 {
583  return (the_node == _Chain_Immutable_head( the_chain ));
584 }
585 
599  const Chain_Control *the_chain,
600  const Chain_Node *the_node
601 )
602 {
603  return (the_node == _Chain_Immutable_tail( the_chain ));
604 }
605 
614  Chain_Control *the_chain
615 )
616 {
617  Chain_Node *head;
618  Chain_Node *tail;
619 
620  _Assert( the_chain != NULL );
621 
622  head = _Chain_Head( the_chain );
623  tail = _Chain_Tail( the_chain );
624 
625  head->next = tail;
626  head->previous = NULL;
627  tail->previous = head;
628 }
629 
640  Chain_Node *the_node
641 )
642 {
643  Chain_Node *next;
644  Chain_Node *previous;
645 
646  next = the_node->next;
647  previous = the_node->previous;
648  next->previous = previous;
649  previous->next = next;
650 }
651 
668  Chain_Control *the_chain
669 )
670 {
671  Chain_Node *head = _Chain_Head( the_chain );
672  Chain_Node *old_first = head->next;
673  Chain_Node *new_first = old_first->next;
674 
675  head->next = new_first;
676  new_first->previous = head;
677 
678  return old_first;
679 }
680 
696  Chain_Control *the_chain
697 )
698 {
699  if ( !_Chain_Is_empty(the_chain))
700  return _Chain_Get_first_unprotected(the_chain);
701  else
702  return NULL;
703 }
704 
719  Chain_Node *after_node,
720  Chain_Node *the_node
721 )
722 {
723  Chain_Node *before_node;
724 
725  the_node->previous = after_node;
726  before_node = after_node->next;
727  after_node->next = the_node;
728  the_node->next = before_node;
729  before_node->previous = the_node;
730 }
731 
744  Chain_Control *the_chain,
745  Chain_Node *the_node
746 )
747 {
748  Chain_Node *tail = _Chain_Tail( the_chain );
749  Chain_Node *old_last = tail->previous;
750 
751  the_node->next = tail;
752  tail->previous = the_node;
753  old_last->next = the_node;
754  the_node->previous = old_last;
755 }
756 
767  Chain_Control *the_chain,
768  Chain_Node *the_node
769 )
770 {
771  if ( _Chain_Is_node_off_chain( the_node ) ) {
772  _Chain_Append_unprotected( the_chain, the_node );
773  }
774 }
775 
788  Chain_Control *the_chain,
789  Chain_Node *the_node
790 )
791 {
792  _Chain_Insert_unprotected(_Chain_Head(the_chain), the_node);
793 }
794 
807  Chain_Control *the_chain,
808  Chain_Node *the_node
809 )
810 {
811  _Chain_Insert(_Chain_Head(the_chain), the_node);
812 }
813 
829  Chain_Control *the_chain,
830  Chain_Node *the_node
831 )
832 {
833  bool was_empty = _Chain_Is_empty( the_chain );
834 
835  _Chain_Append_unprotected( the_chain, the_node );
836 
837  return was_empty;
838 }
839 
855  Chain_Control *the_chain,
856  Chain_Node *the_node
857 )
858 {
859  bool was_empty = _Chain_Is_empty( the_chain );
860 
861  _Chain_Prepend_unprotected( the_chain, the_node );
862 
863  return was_empty;
864 }
865 
885  Chain_Control *the_chain,
886  Chain_Node **the_node
887 )
888 {
889  bool is_empty_now = true;
890  Chain_Node *head = _Chain_Head( the_chain );
891  Chain_Node *tail = _Chain_Tail( the_chain );
892  Chain_Node *old_first = head->next;
893 
894  if ( old_first != tail ) {
895  Chain_Node *new_first = old_first->next;
896 
897  head->next = new_first;
898  new_first->previous = head;
899 
900  *the_node = old_first;
901 
902  is_empty_now = new_first == tail;
903  } else
904  *the_node = NULL;
905 
906  return is_empty_now;
907 }
908 
918 typedef bool ( *Chain_Node_order )(
919  const Chain_Node *left,
920  const Chain_Node *right
921 );
922 
935  Chain_Control *chain,
936  Chain_Node *to_insert,
937  Chain_Node_order order
938 )
939 {
940  const Chain_Node *tail = _Chain_Immutable_tail( chain );
941  Chain_Node *next = _Chain_First( chain );
942 
943  while ( next != tail && !( *order )( to_insert, next ) ) {
944  next = _Chain_Next( next );
945  }
946 
947  _Chain_Insert_unprotected( _Chain_Previous( next ), to_insert );
948 }
949 
952 #ifdef __cplusplus
953 }
954 #endif
955 
956 #endif
957 /* end of include file */
RTEMS_INLINE_ROUTINE void _Chain_Prepend(Chain_Control *the_chain, Chain_Node *the_node)
Prepend a node (protected).
Definition: chainimpl.h:806
RTEMS_INLINE_ROUTINE void _Chain_Append_unprotected(Chain_Control *the_chain, Chain_Node *the_node)
Append a node (unprotected).
Definition: chainimpl.h:743
This is used to manage each element (node) which is placed on a chain.
Definition: chain.h:65
RTEMS_INLINE_ROUTINE Chain_Node * _Chain_Head(Chain_Control *the_chain)
Return pointer to chain head.
Definition: chainimpl.h:301
Chain_Node * previous
This points to the node immediate prior to this one on this chain.
Definition: chain.h:69
Chain_Node * _Chain_Get(Chain_Control *the_chain)
Obtain the first node on a chain.
Definition: chainget.c:26
RTEMS_INLINE_ROUTINE Chain_Node * _Chain_Next(Chain_Node *the_node)
Return pointer the next node from this node.
Definition: chainimpl.h:433
void _Chain_Initialize(Chain_Control *the_chain, void *starting_address, size_t number_nodes, size_t node_size)
Initialize a chain header.
Definition: chain.c:26
bool _Chain_Prepend_with_empty_check(Chain_Control *the_chain, Chain_Node *the_node)
Prepend a node and check if the chain was empty before.
Definition: chainprependempty.c:31
RTEMS_INLINE_ROUTINE Chain_Node * _Chain_Previous(Chain_Node *the_node)
Return pointer the previous node from this node.
Definition: chainimpl.h:465
RTEMS_INLINE_ROUTINE bool _Chain_Prepend_with_empty_check_unprotected(Chain_Control *the_chain, Chain_Node *the_node)
Prepend a node and check if the chain was empty before (unprotected).
Definition: chainimpl.h:854
#define RTEMS_INLINE_ROUTINE
The following (in conjunction with compiler arguments) are used to choose between the use of static i...
Definition: basedefs.h:135
void _Chain_Extract(Chain_Node *the_node)
Extract the specified node from a chain.
Definition: chainextract.c:27
This is used to manage a chain.
Definition: chain.h:83
RTEMS_INLINE_ROUTINE bool _Chain_Are_nodes_equal(const Chain_Node *left, const Chain_Node *right)
Are two nodes equal.
Definition: chainimpl.h:267
RTEMS_INLINE_ROUTINE const Chain_Node * _Chain_Immutable_head(const Chain_Control *the_chain)
Return pointer to immutable chain head.
Definition: chainimpl.h:317
RTEMS_INLINE_ROUTINE bool _Chain_Is_node_off_chain(const Chain_Node *node)
Is the node off chain.
Definition: chainimpl.h:248
RTEMS_INLINE_ROUTINE void _Chain_Extract_unprotected(Chain_Node *the_node)
Extract this node (unprotected).
Definition: chainimpl.h:639
bool(* Chain_Node_order)(const Chain_Node *left, const Chain_Node *right)
Chain node order.
Definition: chainimpl.h:918
RTEMS_INLINE_ROUTINE void _Chain_Initialize_empty(Chain_Control *the_chain)
Initialize this chain as empty.
Definition: chainimpl.h:613
RTEMS_INLINE_ROUTINE const Chain_Node * _Chain_Immutable_previous(const Chain_Node *the_node)
Return pointer the immutable previous node from this node.
Definition: chainimpl.h:481
RTEMS_INLINE_ROUTINE bool _Chain_Is_empty(const Chain_Control *the_chain)
Is the chain empty.
Definition: chainimpl.h:499
Chain_Node * next
This points to the node after this one on this chain.
Definition: chain.h:67
RTEMS_INLINE_ROUTINE bool _Chain_Has_only_one_node(const Chain_Control *the_chain)
Does this chain have only one node.
Definition: chainimpl.h:558
RTEMS_INLINE_ROUTINE Chain_Node * _Chain_Get_unprotected(Chain_Control *the_chain)
Get the first node (unprotected).
Definition: chainimpl.h:695
RTEMS_INLINE_ROUTINE bool _Chain_Get_with_empty_check_unprotected(Chain_Control *the_chain, Chain_Node **the_node)
Get the first node and check if the chain is empty afterwards (unprotected).
Definition: chainimpl.h:884
Information Required to Manipulate Physical Addresses.
RTEMS_INLINE_ROUTINE Chain_Node * _Chain_Last(Chain_Control *the_chain)
Return pointer to chain&#39;s last node.
Definition: chainimpl.h:400
RTEMS_INLINE_ROUTINE bool _Chain_Append_with_empty_check_unprotected(Chain_Control *the_chain, Chain_Node *the_node)
Append a node and check if the chain was empty before (unprotected).
Definition: chainimpl.h:828
size_t _Chain_Node_count_unprotected(const Chain_Control *chain)
Returns the node count of the chain.
Definition: chainnodecount.c:22
RTEMS_INLINE_ROUTINE bool _Chain_Is_last(const Chain_Node *the_node)
Is this the last node on the chain.
Definition: chainimpl.h:537
void _Chain_Insert(Chain_Node *after_node, Chain_Node *the_node)
Insert a node on a chain.
Definition: chaininsert.c:43
#define _Assert(_e)
Assertion similar to assert() controlled via RTEMS_DEBUG instead of NDEBUG.
Definition: assert.h:83
RTEMS_INLINE_ROUTINE const Chain_Node * _Chain_Immutable_first(const Chain_Control *the_chain)
Return pointer to immutable chain&#39;s first node.
Definition: chainimpl.h:383
RTEMS_INLINE_ROUTINE Chain_Node * _Chain_Tail(Chain_Control *the_chain)
Return pointer to chain tail.
Definition: chainimpl.h:333
RTEMS_INLINE_ROUTINE const Chain_Node * _Chain_Immutable_next(const Chain_Node *the_node)
Return pointer the immutable next node from this node.
Definition: chainimpl.h:449
bool _Chain_Append_with_empty_check(Chain_Control *the_chain, Chain_Node *the_node)
Append a node and check if the chain was empty before.
Definition: chainappendempty.c:31
RTEMS_INLINE_ROUTINE Chain_Node * _Chain_First(Chain_Control *the_chain)
Return pointer to chain&#39;s first node.
Definition: chainimpl.h:366
RTEMS_INLINE_ROUTINE void _Chain_Insert_unprotected(Chain_Node *after_node, Chain_Node *the_node)
Insert a node (unprotected).
Definition: chainimpl.h:718
bool _Chain_Get_with_empty_check(Chain_Control *the_chain, Chain_Node **the_node)
Get the first node and check if the chain is empty afterwards.
Definition: chaingetempty.c:31
void _Chain_Append(Chain_Control *the_chain, Chain_Node *the_node)
Append a node on the end of a chain.
Definition: chainappend.c:41
Chain Handler API.
RTEMS_INLINE_ROUTINE bool _Chain_Is_tail(const Chain_Control *the_chain, const Chain_Node *the_node)
Is this node the chail tail.
Definition: chainimpl.h:598
RTEMS_INLINE_ROUTINE bool _Chain_Is_first(const Chain_Node *the_node)
Is this the first node on the chain.
Definition: chainimpl.h:519
RTEMS_INLINE_ROUTINE Chain_Node * _Chain_Get_first_unprotected(Chain_Control *the_chain)
Get the first node (unprotected).
Definition: chainimpl.h:667
RTEMS_INLINE_ROUTINE void _Chain_Set_off_chain(Chain_Node *node)
Set off chain.
Definition: chainimpl.h:230
RTEMS_INLINE_ROUTINE void _Chain_Insert_ordered_unprotected(Chain_Control *chain, Chain_Node *to_insert, Chain_Node_order order)
Inserts a node into the chain according to the order relation.
Definition: chainimpl.h:934
RTEMS_INLINE_ROUTINE bool _Chain_Is_null_node(const Chain_Node *the_node)
Is the chain node pointer NULL.
Definition: chainimpl.h:285
RTEMS_INLINE_ROUTINE const Chain_Node * _Chain_Immutable_tail(const Chain_Control *the_chain)
Return pointer to immutable chain tail.
Definition: chainimpl.h:349
RTEMS_INLINE_ROUTINE bool _Chain_Is_head(const Chain_Control *the_chain, const Chain_Node *the_node)
Is this node the chain head.
Definition: chainimpl.h:578
RTEMS_INLINE_ROUTINE const Chain_Node * _Chain_Immutable_last(const Chain_Control *the_chain)
Return pointer to immutable chain&#39;s last node.
Definition: chainimpl.h:417
RTEMS_INLINE_ROUTINE void _Chain_Append_if_is_off_chain_unprotected(Chain_Control *the_chain, Chain_Node *the_node)
Append a node on the end of a chain if the node is in the off chain state (unprotected).
Definition: chainimpl.h:766
RTEMS_INLINE_ROUTINE void _Chain_Prepend_unprotected(Chain_Control *the_chain, Chain_Node *the_node)
Prepend a node (unprotected).
Definition: chainimpl.h:787