⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 keyboard.c

📁 用ST92163开发的鼠标
💻 C
📖 第 1 页 / 共 2 页
字号:
	BYTE	bit ;
	BYTE	col = 0 ;

	/* Poll Row0 */
	P3DR = 0x7F ;
	cols[ col] = get_key() ;
	col += 1 ;
	P3DR = 0xFF ;
	
	/* Poll Row1 */
	P1DR = 0x40 ;
	cols[ col] = get_key() ;
	col += 1 ;
	P1DR = 0xFF ;
	
	/* Poll Row2-7 */
	spp( P6C_PG) ;
	for( bit = 0x20 ; bit ; bit >>= 1)
	{
		P6DR = ~bit ;
		cols[ col] = get_key() ;
		col += 1 ;
	}

	P6DR = 0xFF ;

	/* Poll Row8-14 */
	for( bit = 1 ; bit < 0x80 ; bit <<= 1)
	{
		P5DR = ~bit ;
		cols[ col] = get_key() ;
		col += 1 ;
	}

	P5DR = 0xFF ;

//	if( !configuration_status[ 3])	/* Joystick is not active */
//	{
//		P5DR = 0x7F ;
//		cols[ col] = get_key() ;
//		P5DR = 0xFF ;
//	}

/* Row 15: Joystick buttons */
	P5DR = 0x7F ;
	cols[ col] = get_key() ;
	P5DR = 0xFF ;
}

BYTE	ghost_f ;

static BYTE check_ghost( void)
{
	BYTE i, j, t ;

	for( i = 0 ; i < 15 ; i++)
	{
		for( j = i + 1 ; j < 16 ; j++)
		{
			if( cols[ i] & cols[ j])	/* At least one bit in common */
			{
				t = cols[ i] | cols[ j] ;	/* Ghost key effect */
				if( t & ~( t & -t))		/* Check at least 2 bits */
					return 1 ;
			}
		}
	}

	return 0 ;
#if 0		
		j = cols[ i] ;
		if( j & ~( j & -j))	/* if at least 2 bits are set */
		{
			BYTE	sum ;

			sum = 0 ;		
			for( j = i + 1 ; j < 16 ; j++)
			{
//				if( i != j)
//					sum |= cols[ j] ;
//			}
		
				if( cols[ i] & cols[ j])
				{
					return 1 ;
				}
			}
		}
	}
	
	return 0 ;
#endif
}

void kbd_poll( void)
{
	BYTE	col ;

	cols_poll() ;
	ghost_f = check_ghost() ;
	if( ghost_f)
	{
		kbd_rollover() ;
	}
	else
	{
		kbd_idx = 2 ;	/* Index for insertion in Buffer */
		kbd_Buffer[ 0] = kbd_Buffer[ 1] = 0 ;
		for( col = 0 ; col < 15 ; col++)
		{
			if( cols[ col] != 0)
				do_col( col, cols[ col]) ;
		}

		if( configuration_status[ 3])	/* Joystick is active */
		{
			extern BYTE j_buttons ;
			
			j_buttons = cols[ 15] ;
		}
		else
		{
			extern BYTE x, y ;                              
	
			if( cols[ 15])
				do_col( 15, cols[ 15]) ;

			get_xy() ;
			if( y < 64)
				kbd_insert( 0x52) ;

			if( y > 192)
				kbd_insert( 0x51) ;


			if( x >192)	/* Right */
				kbd_insert( 0x4F) ;


			if( x < 64)	/* Left */
				kbd_insert( 0x50) ;
		}

		while( kbd_idx < 8)
		{
			kbd_Buffer[ kbd_idx++] = 0x00 ;
		}
	}
}

void KEYBOARD_proc( void)
{
	if( configuration_status[ 1])
	{
		spp( 4) ;
		if( (ENDPR3_A & 0x30) == 0x20 /* STAT_NAK */)
		{
			BYTE i, change ;

			kbd_poll() ;
//			if( !ghost_f)
//			{
				change = 0 ;
				for( i = 0 ; i < 8 ; i++)
				{
					if( kbd_tmp[ i] != kbd_Buffer[ i])
					{
						change = 1 ;
					}
				
					kbd_tmp[ i] = kbd_Buffer[ i] ;
				}

				if( kbd_tmp[ 0] == 0x01 && kbd_tmp[ 2] == KL1 && kbd_tmp[ 4] == 0)
				{
					switch( kbd_tmp[ 3])
					{
					case KF19:	/* USB European */
						scanmap = &scancode[ 0] ;
						change = 0 ;
						break ;
					case KF20:	/* UK -> US */
						scanmap = &scancode[ 1] ;
						change = 0 ;
						break ;
					case KF21:	/* GE -> US */
						scanmap = &scancode[ 2] ;
						change = 0 ;
						break ;
					case KF22:	/* FR -> US */
						scanmap = &scancode[ 3] ;
						change = 0 ;
						break ;
					case KF23:	/* IT -> US */
						scanmap = &scancode[ 4] ;
						change = 0 ;
						break ;
					case KF24:	/* SP -> US */
						scanmap = &scancode[ 5] ;
						change = 0 ;
						break ;
					}
				}
				
				if( change)
					KEYBOARD_Send() ;
//			}
		}
	}
}

void KEYBOARD_Send( void)
{
	EP3TxAddr = kbd_Buffer ;
	EP3TxCount = sizeof kbd_Buffer ;
	spp( 4) ;
	ENDPR3_A |= 0x30 ;	/* Tx Valid */
}

void KEYBOARD_reset( void)
{
/* Always called in Endpoint 0 (HUB) context */
	spp( 4) ;
	ENDPR2_A |= 0x02 ;	/* Control endpoint */

	EP2RxAddr = RxBuffer[ 1] ;
	EP2RxCount = MAX_PACKET_SIZE ;
	EP2TxAddr = 0 ;	/* Insure there is a valid Tx address in case of a STATUS IN */

	ENDPR2_A &= ~0x30 ;		/* EP2 TX STAT_DISABLED */
	ENDPR2_B |= 0x30 ;		/* EP2 RX STAT_VALID */

	/* INT IN */
	ENDPR3_A &= ~0x30 ;		/* EP3 TX STAT_DISABLED */
	ENDPR3_B &= ~0x30 ; 	/* EP3 RX STAT_DISABLED */
	ENDPR3_B |= 0x1 ;		/* EP3 is Device 1 Endpoint 1 */

	spp( USB_PG) ;
	DADDR1 = 0 | 0x80 ;		/* EP0 default address */
}

void KEYBOARD_set_configuration( BYTE configuration_status)
{
/* Called in the CTL endpoint context */
	if( configuration_status == 0)
	{
	/* device is not configured */
		ENDPR3_A &= ~0x30 ;		/* Disable Tx */
	}
	else
	{
	/* device is configured */
		scanmap = &scancode[ 0] ;
		ENDPR3_A &= ~0x70 ;
		ENDPR3_A |= 0x20 ; /* Tx STAT_NAK */
	}
}

#pragma INTERRUPT ep2_int
void ep2_int( void)
{
	spp( 4) ;

	if( ENDPR2_A == 0xEE)	/* Correct SETUP received */
	{
		ENDPR2_B |= 0x80 ;	/* By default we expect STATUS_OUT */
		CurDevice = 1 ;
		CurRxBuffer = (BYTE *) EP2RxAddr ;
		fsm_state[ 1] = do_setup() ;
		switch( fsm_state[ 1])
		{
			case TX_STALL:
				ENDPR2_A &= ~0x30 ;	/* Clear STAT bits */
				ENDPR2_A |= 0x10 ;		/* Tx STAT_STALL */
				break ;
			case TX_N:
				EP2TxAddr = data_ptr ;
				if( data_size[ 1] >= MAX_PACKET_SIZE)
				{
					EP2TxCount = MAX_PACKET_SIZE ;
				}
				else
				{
					EP2TxCount = data_size[ 1] ;
					fsm_state[ 1] = TX_LAST ;
				}
		
				ENDPR2_A |= 0x30 ;	/* TX STAT_VALID */
				break ;
			case TX_ACK_ADDR:
			case TX_0:
				EP2TxCount = 0 ;					/* Enable the transmission */
				ENDPR2_A |= 0x30 ;
				break ;
			default:
				nop() ;
		}
	}
	else if( (ENDPR2_A & 0xBF) == 0xAA)	/* IN (don't care toggle) */
	{
		switch( fsm_state[ 1])
		{
			case TX_N:	/* after IN( n) => send next */
				EP2TxAddr += EP2TxCount ;
				data_size[ 1] -= EP2TxCount ;
				if( data_size[ 1] < MAX_PACKET_SIZE)
				{
					EP2TxCount = data_size[ 1] ;
					fsm_state[ 1] = TX_LAST ;
				}

				ENDPR2_A |= 0x30 ;	/* Tx STAT_VALID */				
				break ;
			case TX_LAST:	/* after a IN( 0) => expect STATUS_OUT */
				break ;
			case TX_ACK_ADDR:
				spp( USB_PG) ;
				DADDR1 = 0x80 | address[ 1] ;
				spp( 4) ;
				/* Fall Through */
			case TX_0:	/* STATUS_IN */
				fsm_state[ 1] = UNDEFINED ;
				break ;
		}
	}
	else if( (ENDPR2_A & 0x8F) == 0x82)	/* OUT (don't care Tx STAT */
	{
		switch( fsm_state[ 1])
		{
			case TX_N:	/* HOST stops transmission */
				ENDPR2_A &= ~0x30 ;	/* Tx STAT_DISABLE */
				/* Fall Through */
			case TX_LAST:	/* Status_out following transmission */
				fsm_state[ 1] = UNDEFINED ;				
		}
	}

	EP2RxCount = MAX_PACKET_SIZE ;
	ENDPR2_B |= 0x30 ; /* Rx STAT_VALID */
	ENDPR2_A &= ~0x80 ;	/* Reset CTR */		
}

#pragma INTERRUPT ep3_int
void ep3_int( void)
{
	spp( 4) ;
	ENDPR3_A &= ~0x80 ;	/* Reset CTR bit */
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -