LLMACRO.H
//--llmacro.h------------------------------------------------------------------ 
// 
// Linked list macros. 
// 
// Copyright (C) Microsoft Corp., 1986-1996.  All rights reserved. 
// 
//----------------------------------------------------------------------------- 
 
#ifndef_LLMACRO_H 
#define _LLMACRO_H 
 
// 
// Single linked list manipulation macros. 
// 
 
// 
// Linked lists maintained by these macros are assumed to look like this: 
// 
//  ________      ________      ________ 
//      |        |    |        |    |        | 
//      |        |    |        |    |        | 
// list head ptr --->|  head  |--->| middle |--->|  tail  |---> NULL 
//      |        |    |  ...   |    |        | 
//      |        |    |        |    |        |<---- 
//      |________|    |________|    |________|    / 
//                                                             / 
// list tail ptr ----------------------------------------------- 
// 
// The macro parameters used are: 
// 
//  np -node ptr for node being added, removed, etc. 
//  hd -list head ptr, as shown above 
//  tl -list tail ptr, as shown above 
// 
 
#define AddToSLLHead(np, hd, tl)\ 
{\ 
  if (!(hd))\ 
    (tl)= (np);\ 
  (np)->m_pNxt= (hd);\ 
  (hd)= (np);\ 
} 
 
#define AddToSLLTail(np, hd, tl)\ 
{\ 
  if (hd)\ 
  {\ 
    (tl)->m_pNxt= (np);\ 
    (tl)= (np);\ 
  }\ 
  else\ 
    (hd) = (tl) = (np);\ 
} 
 
#define RmFromSLLHead(np, hd, tl)\ 
{\ 
  (np)= (hd);\ 
  (hd)= (hd)->m_pNxt;\ 
  if (!(hd))\ 
    (tl) = NULL;\ 
} 
 
// 
// Double linked list manipulation macros. 
// 
 
// 
// Linked lists maintained by these macros are assumed to look like this: 
// 
//                    ________      ________      ________ 
//     |        |    |        |    |        | 
// list head ptr --->|        |--->|        |--->|        |---> NULL 
//                   |  head  |    | middle |    |  tail  | 
//  ---|        |<---|  ...   |<---|        |<--- 
//  /  |________|    |________|    |________|   / 
//                /                                           / 
//                --------------------------------------------- 
// 
// The macro parameters used are: 
// 
//  np -node ptr for node being added, removed, etc. 
//  lp -list head ptr, as shown above. 
//  pn -previous node ptr, points at node after which an insertion 
//is to be done 
// 
// NOTE that care must be taken in using these macros in a conditional statement 
// (if ... else) due to the potential impact of the braces in the macros on 
// the logic of the conditional statement. 
// 
// 
 
#defineAddToDLLHead(np, lp)\ 
{\ 
  if ((lp))\ 
  {\ 
    (np)->m_pPrv= (lp)->m_pPrv;\ 
    (lp)->m_pPrv= (np);\ 
  }\ 
  else\ 
    (np)->m_pPrv= (np);\ 
  (np)->m_pNxt = (lp);\ 
  (lp)= (np);\ 
} 
 
#defineAddToDLLTail(np, lp)\ 
{\ 
  (np)->m_pNxt= NULL;\ 
  if ((lp))\ 
  {\ 
    (np)->m_pPrv= (lp)->m_pPrv;\ 
    (lp)->m_pPrv->m_pNxt= (np);\ 
    (lp)->m_pPrv= (np);\ 
  }\ 
  else\ 
  {\ 
    (np)->m_pPrv= (np);\ 
    (lp)= (np);\ 
  }\ 
} 
 
// 
// InsertIntoDLL() assumes: 
// 
//lp != NULL 
//pn != NULL 
//pn is a node in lp 
// 
 
#defineInsertIntoDLL(np, lp, pn)\ 
{\ 
  if ((pn)->m_pNxt)\ 
  {\ 
    (pn)->m_pNxt->m_pPrv= (np);\ 
    (np)->m_pNxt= (pn)->m_pNxt;\ 
  }\ 
  else\ 
  {\ 
    (np)->m_pNxt= NULL;\ 
    (lp)->m_pPrv= (np);\ 
  }\ 
  (pn)->m_pNxt= (np);\ 
  (np)->m_pPrv= (pn);\ 
} 
 
#defineRmFromDLL(np, lp)\ 
{\ 
  if ((np)->m_pNxt) \ 
  {\ 
    (np)->m_pNxt->m_pPrv= (np)->m_pPrv;\ 
    if ((np) == (lp))\ 
      (lp)= (np)->m_pNxt;\ 
    else\ 
      (np)->m_pPrv->m_pNxt= (np)->m_pNxt;\ 
  }\ 
  else\ 
  {\ 
    if ((np) == (lp))\ 
      (lp)= NULL;\ 
    else\ 
    {\ 
      (np)->m_pPrv->m_pNxt= NULL;\ 
      (lp)->m_pPrv= (np)->m_pPrv;\ 
    }\ 
  }\ 
} 
 
#defineRmFromDLLHead(np, lp)\ 
{\ 
  (np) = (lp);\ 
  if ((lp)->m_pNxt)\ 
  {\ 
    (lp)->m_pNxt->m_pPrv= (lp)->m_pPrv;\ 
    (lp)= (lp)->m_pNxt;\ 
  }\ 
  else\ 
    (lp)= NULL;\ 
} 
 
#endif// _LLMACRO_H