#include        <HE5_HdfEosDef.h>

#define  FILENAME   "Alias.he5"
#define  RANK       2

main()
{
  herr_t       status = FAIL;
  
  int          i, j;
  int          rank       = FAIL;
  int          length     = 0;
  int          attr[1]    = {2000};
  int          fieldgroup = FAIL;

  H5T_class_t  dtype   = H5T_NO_CLASS; 
  hid_t        dtype1  = FAIL;
  H5T_order_t  order   = H5T_ORDER_ERROR;

  long         nattr      = FAIL;
  long         strbufsize = FAIL; 
  long         nfldalias     = FAIL;
  long         nalias = FAIL;

  hid_t        GDid = FAIL, gdfid = FAIL;
  hid_t        datatype = FAIL;
  
  float        out_buffer[ 200 ][ 120 ];
  float        fillvalue = -777.777;
  float        out_fillvalue = -1.;

  size_t       size    = 0;

  hssize_t     start[ 3 ];
  hsize_t      edge[ 3 ];
  hsize_t      count[3];
  hsize_t      nelem = 0;
  hsize_t      dims[8] = {0, 0, 0, 0, 0, 0, 0, 0};
  
  char         dimlist[80];
  char         maxdimlist[80];
  char         *namebuf, attrlist[80];

  int          zonecode, spherecode;
 
  long         xdim, ydim;
 
  double       projparm[16], uplft[2], lowrgt[2];
  int          tilerank, compcode = 16;
  int          compparm[5] = {0, 0, 0, 0, 0};
  hsize_t      tiledims[8];
  float        veg[200][120];
  char         fldalias[80];
  char         aliaslist[80];

  /* Fill veg array */
  for (i = 0; i < 200; i++)
        for (j = 0; j < 120; j++)
          veg[i][j] = (float)(10+i);

  /* 
   *****************************************************************************
   *                 Open/Create the Grid "UTMGrid"                             *
   *****************************************************************************
   */
  
  gdfid = HE5_GDopen(FILENAME, H5F_ACC_TRUNC);
  printf("Grid file ID                      = %d\n", gdfid);

  zonecode   = 40;
  spherecode = 0;
 
  /* Upper Left and Lower Right points in meters */
  /* ------------------------------------------- */
  uplft[0]   =   210584.50041;
  uplft[1]   =  3322395.95445;
  lowrgt[0]  =  813931.10959;
  lowrgt[1]  = 2214162.53278;
 
  xdim = 120;
  ydim = 200;
 
  GDid   = HE5_GDcreate(gdfid, "UTMGrid", xdim, ydim, uplft, lowrgt);
  printf("Grid ID returned by HE5_GDcreate :                    %d \n", GDid);
 
  status = HE5_GDdefproj(GDid, HE5_GCTP_UTM, zonecode, spherecode, projparm);
  printf("status returned by HE5_GDdefproj(...\"HE5_GCTP_UTM\"...) :  %d \n", status);

  status = HE5_GDsetfillvalue(GDid, "Vegetation", H5T_NATIVE_FLOAT, &fillvalue);
  printf("Status returned by HE5_GDsetfillvalue(...,\"Vegetation\",...) : %d \n", status);
 
  /* Define appendable field "Vegetation"  */
  tilerank    = 2;
  tiledims[0] = 100;
  tiledims[1] = 60;
  compparm[0] = 8;

  status = HE5_GDdeftile(GDid,HE5_HDFE_TILE,tilerank,tiledims);
  printf("Status returned by HE5_GDdeftile():                %d\n", status);

  status = HE5_GDdefcomp(GDid,compcode, compparm);
  printf("Status returned by HE5_GDdefcomp():                %d\n", status);

  status = HE5_GDdeffield(GDid, "Vegetation", "YDim,XDim",NULL,H5T_NATIVE_FLOAT, 0);
  printf("Status returned by HE5_GDdeffield(\"Vegetation\"):   %d\n", status);

  start[0] = 0;
  start[1] = 0;
  edge[0]  = 200;   
  edge[1]  = 120;

  status = HE5_GDwritefield(GDid, "Vegetation", start, NULL, edge, veg);
  printf("Status returned by HE5_GDwritefield() :    %d \n", status); 

  /* Set aliases for field "Pollution" */
  /* --------------------------------- */
  status  = HE5_GDsetalias(GDid,"Vegetation","Temp,Vege,L2gpValue,ZZZ");
  printf("status returned by HE5_GDsetalias      = %d\n", status);

  strcpy(fldalias,"");
  nfldalias = HE5_GDinqfldalias(GDid, fldalias, &strbufsize);
  printf("Number of fields & aliases is: %li\n", nfldalias);
  printf("Fields & aliases list:            %s \n", fldalias);
  printf("Length of fields & aliases list:  %li \n", strbufsize);

  strcpy(aliaslist,"");
  nalias = HE5_GDgetaliaslist(GDid, HE5_HDFE_DATAGROUP, aliaslist, &strbufsize);
  printf("Number of aliases is: %li\n", nalias);
  printf("Aliases list:            %s \n", aliaslist);
  printf("Length of aliases list:  %li \n", strbufsize);


  /* Get information about alias "Vege" */
  /* ---------------------------------- */
  status = HE5_GDaliasinfo(GDid,  HE5_HDFE_DATAGROUP, "Vege", &length, NULL);
  if (status == SUCCEED)
	printf("Name length: %d \n", length);
  
  namebuf = (char *)calloc(length, sizeof(char));

  /* Get the actual name of the field "Vege" */
  /* --------------------------------------- */
  status = HE5_GDaliasinfo(GDid,  HE5_HDFE_DATAGROUP, "Vege", &length, namebuf);
  if (status == SUCCEED)
	printf("Original field name: %s \n", namebuf);
  
  free(namebuf);

  /* Remove alias "Temp" from the alias list */
  /* --------------------------------------- */
  status  = HE5_GDdropalias(GDid, HE5_HDFE_DATAGROUP, "Temp");
  printf("status returned by HE5_GDdropalias     = %d\n", status);

  /* Get information about alias  "L2gpValue" */
  /* ---------------------------------------- */  
  status = HE5_GDaliasinfo(GDid,  HE5_HDFE_DATAGROUP, "L2gpValue", &length, NULL);
  if (status == SUCCEED)
	printf("Name length: %d \n", length);
  

  namebuf = (char *)calloc(length, sizeof(char));

  /* Get the actual name of the field "L2gpValue" */
  /* -------------------------------------------- */  
  status = HE5_GDaliasinfo(GDid, HE5_HDFE_DATAGROUP, "L2gpValue", &length, namebuf);
  if (status == SUCCEED)
	printf("Original field name: %s \n", namebuf);
  
  free(namebuf);

  edge[0] = 200;
  edge[1] = 100;
  
  /* Read the data from the field calling it by alias */
  /* ------------------------------------------------ */
  status  = HE5_GDreadfield(GDid,"L2gpValue", start, NULL, edge, out_buffer);
  printf("status returned by HE5_GDreadfield     = %d\n", status);

  printf("Data from \"L2gpValue\" field: \n");
  for ( i = 0; i < 5; i++ )
	for( j = 0; j < 10; j++ )
	  printf("%f \n", out_buffer[ i ][ j ]);

  /* Write local attribute to "L2gpValue" */
  /* ------------------------------------ */
  count[0] = 1;
  status = HE5_GDwritelocattr(GDid, "L2gpValue", "LocalAttribute", H5T_NATIVE_INT, count, attr);
  printf("status returned by HE5_GDwritelocattr  = %d\n", status);


  status = HE5_GDdetach(GDid);
  printf("status returned by HE5_GDdetach        = %d\n", status); 

  GDid = HE5_GDattach(gdfid,"UTMGrid");
  printf("Grid ID returned by HE5_GDattach      = %d\n", GDid); 

  printf("Local Attributes:\n");
  nattr = HE5_GDinqlocattrs(GDid, "L2gpValue", NULL, &strbufsize);
  printf("Number of attributes:      %li \n", nattr);
  printf("Length of attribute list:  %li \n", strbufsize);
  strcpy(attrlist,"");
  nattr = HE5_GDinqlocattrs(GDid, "L2gpValue", attrlist, &strbufsize);
  printf("Attribute list:            %s \n", attrlist);

  printf("Local Attribute:\n");
  status = HE5_GDlocattrinfo(GDid,"ZZZ", "LocalAttribute",&dtype1, &nelem);
  printf("Data type:                 %d\n", dtype1);
  printf("Number of elements:        %lu \n", (unsigned long)nelem);    

  status = HE5_GDfieldinfo(GDid, "L2gpValue", &rank, dims, &dtype1, dimlist, maxdimlist);
  printf("Status returned by HE5_GDfieldinfo	= %d\n", status);
  if (status != FAIL)
	{
	  printf("Field rank:                %d \n", rank);
	  printf("Dimension Sizes: \n");
	  for ( i = 0; i < rank; i++)
		{
		  printf("                           %lu \n", (unsigned long)dims[i]);
		}
  
	  printf("Number type ID:            %d \n", dtype1);  
	  printf("DimList string:            %s \n", dimlist);
	  printf("MaxdimList string:         %s \n", maxdimlist);
	}

  fieldgroup = HE5_HDFE_DATAGROUP;
  status = HE5_GDinqdatatype(GDid, "ZZZ", NULL, fieldgroup, &datatype, &dtype, &order, &size);
  printf("status returned by HE5_GDinqdatatype   = %d \n", status);
  if (status != FAIL)
	{
	  printf("Data type ID:              %d \n", datatype);
	  printf("Data type class ID:        %d \n", dtype);
	  printf("Byte order:                %d \n", order);
	  printf("Data size (bytes):         %d \n", (int)size);        
	}

  status  = HE5_GDcompinfo(GDid,"L2gpValue", &compcode, compparm);
  printf("status returned by HE5_GDcompinfo      = %d\n", status);
  if (status != FAIL)
	{
	  printf("Compression Information: \n");  
	  printf("Compression code:          %d \n", compcode);
	  printf("Compression level:         %d \n", compparm[0]);
	}

  status = HE5_GDgetfillvalue(GDid,"L2gpValue",&out_fillvalue);
  printf("status returned by HE5_GDgetfillvalue  = %d\n", status);
  printf("The fill value:            %f\n", out_fillvalue);

  status = HE5_GDdetach(GDid);
  printf("status returned by HE5_GDdetach        = %d\n", status); 

  status = HE5_GDclose(gdfid);
  printf("status returned by HE5_GDclose         = %d\n", status);
}

















