conteepread.c 3.6 KB

/**************************************************************************
 *                                                                        *
 *               Copyright (C) 1995, Silicon Graphics, Inc.               *
 *                                                                        *
 *  These coded instructions, statements, and computer programs  contain  *
 *  unpublished  proprietary  information of Silicon Graphics, Inc., and  *
 *  are protected by Federal copyright law.  They  may  not be disclosed  *
 *  to  third  parties  or copied or duplicated in any form, in whole or  *
 *  in part, without the prior written consent of Silicon Graphics, Inc.  *
 *                                                                        *
 **************************************************************************/

#include "osint.h"
#include "controller.h"
#include "siint.h"

#pragma pack (8)

#if __GNUC__
OSPifRam		__osEepPifRam __attribute__((aligned (16)));
#else
OSPifRam		__osEepPifRam;		/* EEPROM RAM buffer */
#endif

int		__osEepromRead16K;

static void	__osPackEepReadData(u8);

/*
 * This call issues a read eeprom command to pif to read
 *  8 bytes from eeprom.
 * A value of 0 is returned if the calls succeed, otherwise
 * -1 is returned
 */
s32
osEepromRead(OSMesgQueue *mq, u8 address, u8 *buffer)
{
	s32	ret = 0;
	int 	i=0;
	u16	type;
	u8 			*ptr = (u8 *)(&__osEepPifRam);
	OSContStatus 		sdata;
	__OSContEepromFormat 	eepromformat;

	/* Block to get resource token */
	__osSiGetAccess();

	/* Need to make sure EEPROM is not busy before write */

	ret = __osEepStatus(mq, &sdata);
	type = (u16)(sdata.type & (u16)(CONT_EEPROM | CONT_EEP16K));

	if (ret == 0) {
	  switch(type) {
	  case (u16)CONT_EEPROM :
	    if(address >= EEPROM_MAXBLOCKS) {
	      ret = -1;
	    }
	    break;
	  case (u16)(CONT_EEPROM | CONT_EEP16K) :
	    if(address >= EEP16K_MAXBLOCKS) {
	      ret = -1;
	    } else {
	      __osEepromRead16K = 1;
	    }
	    break;
	  default:
	    ret = CONT_NO_RESPONSE_ERROR;
	  }
	}
	if (ret != 0)  {
	  __osSiRelAccess();
	  return(ret);
	}
	
	while (sdata.status & CONT_EEPROM_BUSY) {
		__osEepStatus(mq, &sdata);
	}
		
	/* Set up request command format for eeprom */

	__osPackEepReadData(address);
	ret = __osSiRawStartDma(OS_WRITE, &__osEepPifRam);
	(void)osRecvMesg(mq, (OSMesg *)NULL, OS_MESG_BLOCK);

	/* trigger pifmacro */

	 ret = __osSiRawStartDma(OS_READ, &__osEepPifRam);
	__osContLastCmd = CONT_EEPROM_READ;

	(void)osRecvMesg(mq, (OSMesg *)NULL, OS_MESG_BLOCK);
	for (i = 0; i < MAXCONTROLLERS; i++)
			ptr++;

	eepromformat = *((__OSContEepromFormat *)ptr);
#ifndef _HW_VERSION_1
	ret = (s32)((eepromformat.rxsize & CON_ERR_MASK) >> 4);
#endif
	if (ret == 0) {
		for (i = 0; i < EEPROM_BLOCK_SIZE ; i++)
			*buffer++ = eepromformat.data[i];
	}
	__osSiRelAccess();
	return(ret);
}

static void
__osPackEepReadData(u8 address)
{
	u8 			*ptr = (u8 *)(&__osEepPifRam);
	__OSContEepromFormat 	eepromformat;
	int 			i;

	/* clear pif ram */

#if	0
	for (i = 0; i < PIFRAMSIZE-1 ; i++)
		__osEepPifRam.ramarray[i] = 0xff;
#endif
#ifndef _HW_VERSION_1
	__osEepPifRam.pifstatus = CONT_FORMAT;
#else
	__osEepPifRam.pifstatus = 0;
#endif 


	/* Setup eeprom format */

        eepromformat.txsize = 2;
        eepromformat.rxsize = 8;
        eepromformat.cmd = CONT_EEPROM_READ;
        eepromformat.address = address;

#if	0
        for (i = 0; i < EEPROM_BLOCK_SIZE ; i++)
                eepromformat.data[i] = 0;
#endif

	for (i = 0; i < MAXCONTROLLERS; i++)
		*ptr++ = 0;

        *((__OSContEepromFormat *)ptr) = eepromformat;

#ifndef _HW_VERSION_1
	ptr += sizeof(eepromformat);
	*((u8 *)ptr) = FORMAT_END;
#endif
}