📄 uh1.c
字号:
/*
UH1.C: UH124 user interface library Level 1.
(C) Copyright TransDimension, Inc. All rights reserved.
Modification history
====================
17Aug2000 Original Release
31Jan2001 Modified, JW
20Mar2001 Modified, JW
*/
#include "types.h"
#include "uhc124.h"
#include "uh0.h"
#include "uh1.h"
#include "err.h"
/* enter power saving mode */
void UH_PwrSav(void)
{
UH_Write(UhcControl, CtlPwrSav);
}
/* soft reset */
void UH_SoftReset(void)
{
UH_Write(UhcControl, CtlSoftReset);
}
/* read system operating state */
U8 UH_USBSysState(void)
{
return(UH_Read(UhcControl) & CtlUSBState);
}
/* USB system reset */
void UH_USBReset(void)
{
UH_Write(UhcControl, CtlUSBReset);
}
/* host initiated resume */
I16 UH_USBResume(void)
{
U8 c = UH_USBSysState();
/* invalid unless system in suspend state */
if (c != CtlUSBSuspend) return(ERR_STATE);
UH_Write(UhcControl, CtlUSBResume);
return(ERR_NONE);
}
/* host initiated suspend */
I16 UH_USBSuspend(void)
{
U8 c = UH_USBSysState();
/* invalid unless system in operational state */
if (c != CtlUSBOperational) return(ERR_STATE);
UH_Write(UhcControl, CtlUSBSuspend);
return(ERR_NONE);
}
/* enter state USBoperational */
I16 UH_USBOperational(void)
{
U8 c = UH_USBSysState();
/* invalid unless sys in either reset or suspend state */
if (c != CtlUSBReset && c != CtlUSBSuspend)
return(ERR_STATE);
UH_Write(UhcControl, CtlUSBOperational);
return(ERR_NONE);
}
/* set maximum overhead register */
void UH_SetMaxOverhead(U8 mo)
{
UH_Write(UhcMaxOverhead, mo);
}
/* read maximum overhead register */
U8 UH_MaxOverhead(void)
{
return(UH_Read(UhcMaxOverhead));
}
/* read frame number register */
U16 UH_FmNumber(void)
{
U16 c = UH_Read(UhcFmNumber);
U16 d = UH_Read(UhcFmNumber+1);
return(((d << 8) | c) & 0x7ff);
}
/* read frame remaining register */
U16 UH_FmRemaining(void)
{
U16 c = UH_Read(UhcFmRemaining);
U16 d = UH_Read(UhcFmRemaining+1);
return(((d << 8) | c) & 0x3fff);
}
/* read frame interval register */
U16 UH_FmInterval(void)
{
U16 c = UH_Read(UhcFmInterval+1);
return(((c << 8) | UH_Read(UhcFmInterval)) & 0x3fff);
}
/* set frame interval register */
void UH_SetFmInterval(U16 intv)
{
intv &= 0x3fff;
UH_Write(UhcFmInterval, (U8) (intv & 0xff));
UH_Write(UhcFmInterval+1, (U8) ((intv >> 8) & 0xff));
}
/* read magic number register */
U8 UH_MagicNumber(void)
{
return(UH_Read(UhcMagicNumber));
}
/* read transaction select register */
U16 UH_TransSel(void)
{
U16 c = UH_Read(UhcTransSel+1);
return((U16) ((c << 8) | UH_Read(UhcTransSel)));
}
/* set transaction select register */
I16 UH_SetTransSel(U16 sel)
{
U8 c = UH_Read(UhcControl);
/* cannot set this register if batch on */
if (c & CtlBatchOn) return(ERR_BATCH);
/* write register */
UH_Write(UhcTransSel, (U8) (sel & 0xff));
UH_Write(UhcTransSel+1, (U8) ((sel >> 8) & 0xff));
return(ERR_NONE);
}
/* read transaction done register */
U16 UH_TransDone(void)
{
U16 c = UH_Read(UhcTransDone+1);
return((U16) ((c << 8) | UH_Read(UhcTransDone)));
}
/* read interrupt enable register */
U8 UH_IntpEnb(void)
{
return((U8) (UH_Read(UhcIntpEnb) & INTP_MASK));
}
/* set interrupt enable register */
void UH_SetIntpEnb(U8 mask)
{
UH_Write(UhcIntpEnb, (U8) (mask & INTP_MASK));
}
/* interrupt status clear */
void UH_ClrIntpStatus(U8 mask)
{
UH_Write(UhcIntpStatus, (U8) (mask & INTP_MASK));
}
/* read interrupt status */
U8 UH_IntpStatus(void)
{
return((U8) (UH_Read(UhcIntpStatus) & INTP_MASK));
}
/* prepare XD for a setup xact */
void UH_DispSetup(U8 xd, U8 dev, U8 ep,
U16 setup, U8 stop, U8 spd)
{
U16 b = MXFD_BASE + ((xd &= 0xf) << 4);
/* XD control word */
UH_Write(b+XDControl,
(U8) (XDCTL_SETUP |
((spd) ? XDCTL_LSPD : XDCTL_FSPD) |
(stop & XDCtlStop)));
/* device address and endpoint number */
UH_Write(b+XDDevAddr, dev);
UH_Write(b+XDEpNum, ep);
/* data buf address */
UH_Write(b+XDBufAddr, (U8)(setup & 0xff));
UH_Write(b+XDBufAddr+1, (U8)((setup >> 8) & 0xff));
/* data length */
UH_Write(b+XDBufLen, SP_SIZE);
UH_Write(b+XDBufLen+1, 0);
}
/* prepare an IN or OUT transaction */
void UH_DispData(U8 xd, U8 dev, U8 ep,
U16 data, U16 len, U8 ctl, U8 stop, U8 spd)
{
U16 b = MXFD_BASE + (xd << 4);
U8 c;
/* control word */
c = ((ctl & CTL_DIR) ? XDCTL_IN : XDCTL_OUT) |
(stop & XDCtlStop);
if (spd) c |= XDCTL_LSPD;
if ((ctl & (CTL_DIR | CTL_SEQ | CTL_ISO)) ==
(CTL_OUT | CTL_DATA1))
c |= XDCTL_DATA1;
if (ctl & CTL_ISO) c |= XDCTL_ISO;
UH_Write(b+XDControl, c);
/* device address and endpoint number */
UH_Write(b + XDDevAddr, dev);
UH_Write(b + XDEpNum, ep);
/* data/buffer address */
UH_Write(b+XDBufAddr, (U8)(data & 0xff));
UH_Write(b+XDBufAddr+1, (U8)((data >> 8) & 0xff));
/* data length */
UH_Write(b+XDBufLen, (U8)(len & 0xff));
UH_Write(b+XDBufLen+1, (U8)((len >> 8) & 0xff));
}
/* read transfer status */
U8 UH_XDStatus(U8 xd)
{
U16 b = MXFD_BASE + (xd << 4);
return(UH_Read(b + XDStatus));
}
/* read XD type */
U8 UH_XDType(U8 xd)
{
U16 b = MXFD_BASE + (xd << 4);
return((U8) (UH_Read(b + XDControl) & XDCtlPid));
}
/* read XD stop */
U8 UH_XDStop(U8 xd)
{
U16 b = MXFD_BASE + (xd << 4);
return((U8) (UH_Read(b + XDControl) & XDCtlStop));
}
/* read buffer address */
U16 UH_XDXferCnt(U8 xd)
{
U16 b = MXFD_BASE + (xd << 4);
U16 c = UH_Read(b + XDXferCnt + 1);
return((U8) (((c << 8) | UH_Read(b+XDXferCnt)) & 0x3ff));
}
/* read xd buf address */
U16 UH_XDBufAddr(U8 xd)
{
U16 b = MXFD_BASE + (xd << 4);
U16 c = UH_Read(b + XDBufAddr + 1);
return((c << 8) | UH_Read(b+XDBufAddr) & 0x7ff | MDAT_BASE);
}
/* read xd buffer length */
U16 UH_XDBufLength(U8 xd)
{
U16 b = MXFD_BASE + (xd << 4);
U16 c = UH_Read(b + XDBufLen + 1);
return((c << 8) | UH_Read(b + XDBufLen) & 0x3ff);
}
/* dispatch a transaction batch */
I16 UH_DispBatch(void)
{
U8 s = UH_Read(UhcControl);
/* invalid if another batch is still on */
if (s & CtlBatchOn) return(ERR_BATCH);
/* invalid unless sys is in operational state */
if ((s & CtlUSBState) != CtlUSBOperational)
return(ERR_STATE);
UH_Write(UhcControl, CtlBatchOn);
return(ERR_NONE);
}
/* wait until batch done, modify for RTOS */
U16 UH_EndBatch(void)
{
/* wait until batch done or stopped - tailor to your own system */
while (!(UH_IntpStatus() & (IntpBatchCompl |
IntpBatchStop)));
/* xd's that are selected but not done */
return(UH_TransSel() & ~UH_TransDone());
}
/* only used for reading port change */
void UH_SetMagicNumber(U8 mn)
{
UH_Write(UhcMagicNumber, mn);
}
/* read port change */
U8 UH_PortChange(void)
{
UH_MagicNumber();
UH_SetMagicNumber(MagicKey1);
UH_SetMagicNumber(MagicKey2);
return(UH_MagicNumber());
}
/* magic reset: used for factory test only */
void UH_MagicReset(void)
{
UH_Write(0x700, 0x00);
UH_USBReset();
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -