/*
 * nasd_decompose.c
 *
 * Decompose a NASD id.
 *
 * Author: Jim Zelenka
 */
/*
 * Copyright (c) of Carnegie Mellon University, 1997,1998,1999.
 *
 * Permission to reproduce, use, and prepare derivative works of
 * this software for internal use is granted provided the copyright
 * and "No Warranty" statements are included with all reproductions
 * and derivative works. This software may also be redistributed
 * without charge provided that the copyright and "No Warranty"
 * statements are included in all redistributions.
 *
 * NO WARRANTY. THIS SOFTWARE IS FURNISHED ON AN "AS IS" BASIS.
 * CARNEGIE MELLON UNIVERSITY MAKES NO WARRANTIES OF ANY KIND, EITHER
 * EXPRESSED OR IMPLIED AS TO THE MATTER INCLUDING, BUT NOT LIMITED
 * TO: WARRANTY OF FITNESS FOR PURPOSE OR MERCHANTABILITY, EXCLUSIVITY
 * OF RESULTS OR RESULTS OBTAINED FROM USE OF THIS SOFTWARE. CARNEGIE
 * MELLON UNIVERSITY DOES NOT MAKE ANY WARRANTY OF ANY KIND WITH RESPECT
 * TO FREEDOM FROM PATENT, TRADEMARK, OR COPYRIGHT INFRINGEMENT.
 */


#include <nasd/nasd_options.h>
#include <nasd/nasd_drive_options.h>
#include <nasd/nasd_types.h>
#include <nasd/nasd_freelist.h>
#include <nasd/nasd_itypes.h>
#include <nasd/nasd_mem.h>
#include <nasd/nasd_cache.h>
#include <nasd/nasd_common.h>

/*
 * Reserved nodes:
 * 0 = null
 * 1 = drive info
 * 2 = partition info
 * 3 = partition objects
 * 4 = trace info
 * 5 = trace data
 *
 * (also update nasd_control.idl if this is updated)
 */
nasd_nodenum_t nasd_reserved_nodes = 6;

nasd_status_t
nasd_od_decompose_control(
  nasd_identifier_t   in_nid,
  nasd_nodenum_t     *nodenump)
{
  nasd_uint64 n64;

  if (in_nid == NASDID_NULL)
    return(NASD_BAD_IDENTIFIER);

  *nodenump = in_nid&0xffffffffUL;
  n64 = in_nid&(~0xffffffffUL);
  if (n64)
    return(NASD_FAIL);
  if ((*nodenump) >= nasd_reserved_nodes)
    return(NASD_FAIL);

  return(NASD_SUCCESS);
}

nasd_status_t
nasd_od_decompose_id(
  nasd_identifier_t   in_nid,
  int                *partnump,
  nasd_nodenum_t     *nodenump,
  nasd_blkno_t       *lvl2_hintp,
  nasd_generation_t  *genp)
{
  nasd_uint64 n64;

  if (in_nid == NASDID_NULL)
    return(NASD_BAD_IDENTIFIER);

  *nodenump = in_nid&0xffffffff;

  n64 = in_nid & nasd_uint64cast(0xfe00000000000000);
  n64 >>= 57;
  n64 &= 0x7f;
  *genp = (nasd_generation_t)n64;

  n64 = in_nid & nasd_uint64cast(0x01e0000000000000);
  n64 >>= 53;
  n64 &= 0xf;
  *partnump = (int)n64;

  n64 = in_nid & nasd_uint64cast(0x000003ff00000000);
  n64 >>= 32;
  n64 &= 0x3ff;
  *lvl2_hintp = (nasd_blkno_t)n64;

  return(NASD_SUCCESS);
}

/* Local Variables:  */
/* indent-tabs-mode: nil */
/* tab-width: 2 */
/* End: */
