Beispiel #1
0
/**Load the context for a channel to SDMA
 *
 * <b>Algorithm:</b>\n
 *   - Send context and poll for answer.
 * 
 * @param *cd_p  channel descriptor for channel 0
 * @param *buf pointer to context data
 * @param channel channel to place the context for
 *
 * @return none
 */
void
iapi_lowSetContext(channelDescriptor * cd_p, void * buf, unsigned char channel)
{ 
	
  bufferDescriptor * local_bd_p;
  
  local_bd_p = (bufferDescriptor *)iapi_Phys2Virt(cd_p->ccb_ptr->baseBDptr);
  
  iapi_SetBufferDescriptor( &local_bd_p[0],
                            C0_SETDM,
							(unsigned char)(BD_DONE | BD_INTR | BD_WRAP|BD_EXTD),
							(unsigned short)(sizeof(contextData)/4),
							 buf,
							 (void *)(2048+(sizeof(contextData)/4)*channel));
							 
  /* Send */
  iapi_lowStartChannel( cd_p->channelNumber );
  iapi_lowSynchChannel( cd_p->channelNumber );

}
/**Load the context for a channel to SDMA
 *
 * <b>Algorithm:</b>\n
 *   - Send context and poll for answer.
 *
 * @param *cd_p  channel descriptor for channel 0
 * @param *buf pointer to context data
 * @param channel channel to place the context for
 *
 * @return none
 */
void
iapi_lowSetContext(channelDescriptor *cd_p, void *buf, unsigned char channel)
{

	bufferDescriptor *local_bd_p;
#ifdef SDMA_SKYE

	unsigned char command = 0;

	local_bd_p =
	    (bufferDescriptor *) iapi_Phys2Virt(cd_p->ccb_ptr->baseBDptr);

	command = channel << 3;
	command = command | C0_SETCTX;
	iapi_SetBufferDescriptor(&local_bd_p[0],
				 command,
				 (unsigned char)(BD_DONE | BD_INTR | BD_WRAP),
				 (unsigned short)(sizeof(contextData) / 4),
				 buf, NULL);
#else

	local_bd_p =
	    (bufferDescriptor *) iapi_Phys2Virt(cd_p->ccb_ptr->baseBDptr);

	iapi_SetBufferDescriptor(&local_bd_p[0],
				 C0_SETDM,
				 (unsigned char)(BD_DONE | BD_INTR | BD_WRAP |
						 BD_EXTD),
				 (unsigned short)(sizeof(contextData) / 4), buf,
				 (void *)(2048 +
					  (sizeof(contextData) / 4) * channel));
#endif
	/* Send */
	iapi_lowStartChannel(cd_p->channelNumber);
	iapi_lowSynchChannel(cd_p->channelNumber);

}
/**Send a command on SDMA's channel zero.
 * Check if buffer descriptor is already used by the sdma, if yes return
 * an error as c0BDNum is wrong.
 *
 * <b>Notes</b>\n
 *  There is an upgrade in the script on the Context load command and
 * the fact that the context structure has a fixed length of 20 or 24
 * depending on SDMA versions.
 *
 * @return
 *   - IAPI_SUCCESS
 *   - -iapi_errno if failure
 */
int
iapi_Channel0Command(channelDescriptor *cd_p, void *buf,
		     unsigned short nbyte, unsigned char command)
{
	channelControlBlock *ccb_p;
	bufferDescriptor *bd_p;
	int result = IAPI_SUCCESS;
	unsigned char chNum;

	/*
	 * Check data structures are properly initialized
	 */
	/* Channel descriptor validity */
	if (cd_p == NULL) {
		result = IAPI_ERR_CD_UNINITIALIZED;
		iapi_errno = result;
		return -result;
	}

	/* Channel control block validity */
	if (cd_p->ccb_ptr == NULL) {
		result = IAPI_ERR_CCB_UNINITIALIZED;
		iapi_errno = result;
		return -result;
	}

	/* Control block & Descriptpor associated with the channel being worked on */
	chNum = cd_p->channelNumber;
	ccb_p = cd_p->ccb_ptr;

	/* Is channel already in use ? */
	if (ccb_p->baseBDptr != NULL) {
		result = IAPI_ERR_BD_ALLOCATED | IAPI_ERR_CH_AVAILABLE | chNum;
		iapi_errno = result;
		return -result;
	}

	/* Allocation of buffer descriptors */
	bd_p = (bufferDescriptor *) MALLOC(sizeof(bufferDescriptor), SDMA_ERAM);
	if (bd_p != NULL) {
		ccb_p->baseBDptr = (bufferDescriptor *) iapi_Virt2Phys(bd_p);
	} else {
		result = IAPI_ERR_BD_ALLOCATION | IAPI_ERR_CH_AVAILABLE | chNum;
		iapi_errno = result;
		return -result;
	}

	/* Buffer descriptor setting */
	iapi_SetBufferDescriptor(bd_p, command, BD_WRAP | BD_DONE | BD_INTR,
				 nbyte, buf, NULL);

	/* Actually the transfer */
	iapi_lowStartChannel(cd_p->channelNumber);
	iapi_lowSynchChannel(cd_p->channelNumber);

	/* Cleaning of allocation */
	FREE(bd_p);
	ccb_p->baseBDptr = NULL;

	return IAPI_SUCCESS;

}