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

📄 uec.c

📁 from wangkj@yahoo.com 电路原理图和详细说明: amd.9966.org或者 arm.9966.org 都是原创,包括boot, loader,u-boot,linu
💻 C
📖 第 1 页 / 共 3 页
字号:
	uec->oldlink = 0;	uec->oldspeed = 0;	uec->oldduplex = -1;	mii_info = malloc(sizeof(*mii_info));	if (!mii_info) {		printf("%s: Could not allocate mii_info", dev->name);		return -ENOMEM;	}	memset(mii_info, 0, sizeof(*mii_info));	mii_info->speed = SPEED_1000;	mii_info->duplex = DUPLEX_FULL;	mii_info->pause = 0;	mii_info->link = 1;	mii_info->advertising = (ADVERTISED_10baseT_Half |				ADVERTISED_10baseT_Full |				ADVERTISED_100baseT_Half |				ADVERTISED_100baseT_Full |				ADVERTISED_1000baseT_Full);	mii_info->autoneg = 1;	mii_info->mii_id = uec->uec_info->phy_address;	mii_info->dev = dev;	mii_info->mdio_read = &read_phy_reg;	mii_info->mdio_write = &write_phy_reg;	uec->mii_info = mii_info;	if (init_mii_management_configuration(uec_regs)) {		printf("%s: The MII Bus is stuck!", dev->name);		err = -1;		goto bus_fail;	}	/* get info for this PHY */	curphy = get_phy_info(uec->mii_info);	if (!curphy) {		printf("%s: No PHY found", dev->name);		err = -1;		goto no_phy;	}	mii_info->phyinfo = curphy;	/* Run the commands which initialize the PHY */	if (curphy->init) {		err = curphy->init(uec->mii_info);		if (err)			goto phy_init_fail;	}	return 0;phy_init_fail:no_phy:bus_fail:	free(mii_info);	return err;}static void adjust_link(struct eth_device *dev){	uec_private_t		*uec = (uec_private_t *)dev->priv;	uec_t			*uec_regs;	struct uec_mii_info	*mii_info = uec->mii_info;	extern void change_phy_interface_mode(struct eth_device *dev,					 enet_interface_e mode);	uec_regs = uec->uec_regs;	if (mii_info->link) {		/* Now we make sure that we can be in full duplex mode.		* If not, we operate in half-duplex mode. */		if (mii_info->duplex != uec->oldduplex) {			if (!(mii_info->duplex)) {				uec_set_mac_duplex(uec, DUPLEX_HALF);				printf("%s: Half Duplex\n", dev->name);			} else {				uec_set_mac_duplex(uec, DUPLEX_FULL);				printf("%s: Full Duplex\n", dev->name);			}			uec->oldduplex = mii_info->duplex;		}		if (mii_info->speed != uec->oldspeed) {			switch (mii_info->speed) {				case 1000:					break;				case 100:					printf ("switching to rgmii 100\n");					/* change phy to rgmii 100 */					change_phy_interface_mode(dev,								ENET_100_RGMII);					/* change the MAC interface mode */					uec_set_mac_if_mode(uec,ENET_100_RGMII);					break;				case 10:					printf ("switching to rgmii 10\n");					/* change phy to rgmii 10 */					change_phy_interface_mode(dev,								ENET_10_RGMII);					/* change the MAC interface mode */					uec_set_mac_if_mode(uec,ENET_10_RGMII);					break;				default:					printf("%s: Ack,Speed(%d)is illegal\n",						dev->name, mii_info->speed);					break;			}			printf("%s: Speed %dBT\n", dev->name, mii_info->speed);			uec->oldspeed = mii_info->speed;		}		if (!uec->oldlink) {			printf("%s: Link is up\n", dev->name);			uec->oldlink = 1;		}	} else { /* if (mii_info->link) */		if (uec->oldlink) {			printf("%s: Link is down\n", dev->name);			uec->oldlink = 0;			uec->oldspeed = 0;			uec->oldduplex = -1;		}	}}static void phy_change(struct eth_device *dev){	uec_private_t	*uec = (uec_private_t *)dev->priv;	uec_t		*uec_regs;	int		result = 0;	uec_regs = uec->uec_regs;	/* Delay 5s to give the PHY a chance to change the register state */	udelay(5000000);	/* Update the link, speed, duplex */	result = uec->mii_info->phyinfo->read_status(uec->mii_info);	/* Adjust the interface according to speed */	if ((0 == result) || (uec->mii_info->link == 0)) {		adjust_link(dev);	}}static int uec_set_mac_address(uec_private_t *uec, u8 *mac_addr){	uec_t		*uec_regs;	u32		mac_addr1;	u32		mac_addr2;	if (!uec) {		printf("%s: uec not initial\n", __FUNCTION__);		return -EINVAL;	}	uec_regs = uec->uec_regs;	/* if a station address of 0x12345678ABCD, perform a write to	MACSTNADDR1 of 0xCDAB7856,	MACSTNADDR2 of 0x34120000 */	mac_addr1 = (mac_addr[5] << 24) | (mac_addr[4] << 16) | \			(mac_addr[3] << 8)  | (mac_addr[2]);	out_be32(&uec_regs->macstnaddr1, mac_addr1);	mac_addr2 = ((mac_addr[1] << 24) | (mac_addr[0] << 16)) & 0xffff0000;	out_be32(&uec_regs->macstnaddr2, mac_addr2);	return 0;}static int uec_convert_threads_num(uec_num_of_threads_e threads_num,					 int *threads_num_ret){	int	num_threads_numerica;	switch (threads_num) {		case UEC_NUM_OF_THREADS_1:			num_threads_numerica = 1;			break;		case UEC_NUM_OF_THREADS_2:			num_threads_numerica = 2;			break;		case UEC_NUM_OF_THREADS_4:			num_threads_numerica = 4;			break;		case UEC_NUM_OF_THREADS_6:			num_threads_numerica = 6;			break;		case UEC_NUM_OF_THREADS_8:			num_threads_numerica = 8;			break;		default:			printf("%s: Bad number of threads value.",				 __FUNCTION__);			return -EINVAL;	}	*threads_num_ret = num_threads_numerica;	return 0;}static void uec_init_tx_parameter(uec_private_t *uec, int num_threads_tx){	uec_info_t	*uec_info;	u32		end_bd;	u8		bmrx = 0;	int		i;	uec_info = uec->uec_info;	/* Alloc global Tx parameter RAM page */	uec->tx_glbl_pram_offset = qe_muram_alloc(				sizeof(uec_tx_global_pram_t),				 UEC_TX_GLOBAL_PRAM_ALIGNMENT);	uec->p_tx_glbl_pram = (uec_tx_global_pram_t *)				qe_muram_addr(uec->tx_glbl_pram_offset);	/* Zero the global Tx prameter RAM */	memset(uec->p_tx_glbl_pram, 0, sizeof(uec_tx_global_pram_t));	/* Init global Tx parameter RAM */	/* TEMODER, RMON statistics disable, one Tx queue */	out_be16(&uec->p_tx_glbl_pram->temoder, TEMODER_INIT_VALUE);	/* SQPTR */	uec->send_q_mem_reg_offset = qe_muram_alloc(				sizeof(uec_send_queue_qd_t),				 UEC_SEND_QUEUE_QUEUE_DESCRIPTOR_ALIGNMENT);	uec->p_send_q_mem_reg = (uec_send_queue_mem_region_t *)				qe_muram_addr(uec->send_q_mem_reg_offset);	out_be32(&uec->p_tx_glbl_pram->sqptr, uec->send_q_mem_reg_offset);	/* Setup the table with TxBDs ring */	end_bd = (u32)uec->p_tx_bd_ring + (uec_info->tx_bd_ring_len - 1)					 * SIZEOFBD;	out_be32(&uec->p_send_q_mem_reg->sqqd[0].bd_ring_base,				 (u32)(uec->p_tx_bd_ring));	out_be32(&uec->p_send_q_mem_reg->sqqd[0].last_bd_completed_address,						 end_bd);	/* Scheduler Base Pointer, we have only one Tx queue, no need it */	out_be32(&uec->p_tx_glbl_pram->schedulerbasepointer, 0);	/* TxRMON Base Pointer, TxRMON disable, we don't need it */	out_be32(&uec->p_tx_glbl_pram->txrmonbaseptr, 0);	/* TSTATE, global snooping, big endian, the CSB bus selected */	bmrx = BMR_INIT_VALUE;	out_be32(&uec->p_tx_glbl_pram->tstate, ((u32)(bmrx) << BMR_SHIFT));	/* IPH_Offset */	for (i = 0; i < MAX_IPH_OFFSET_ENTRY; i++) {		out_8(&uec->p_tx_glbl_pram->iphoffset[i], 0);	}	/* VTAG table */	for (i = 0; i < UEC_TX_VTAG_TABLE_ENTRY_MAX; i++) {		out_be32(&uec->p_tx_glbl_pram->vtagtable[i], 0);	}	/* TQPTR */	uec->thread_dat_tx_offset = qe_muram_alloc(		num_threads_tx * sizeof(uec_thread_data_tx_t) +		 32 *(num_threads_tx == 1), UEC_THREAD_DATA_ALIGNMENT);	uec->p_thread_data_tx = (uec_thread_data_tx_t *)				qe_muram_addr(uec->thread_dat_tx_offset);	out_be32(&uec->p_tx_glbl_pram->tqptr, uec->thread_dat_tx_offset);}static void uec_init_rx_parameter(uec_private_t *uec, int num_threads_rx){	u8	bmrx = 0;	int	i;	uec_82xx_address_filtering_pram_t	*p_af_pram;	/* Allocate global Rx parameter RAM page */	uec->rx_glbl_pram_offset = qe_muram_alloc(		sizeof(uec_rx_global_pram_t), UEC_RX_GLOBAL_PRAM_ALIGNMENT);	uec->p_rx_glbl_pram = (uec_rx_global_pram_t *)				qe_muram_addr(uec->rx_glbl_pram_offset);	/* Zero Global Rx parameter RAM */	memset(uec->p_rx_glbl_pram, 0, sizeof(uec_rx_global_pram_t));	/* Init global Rx parameter RAM */	/* REMODER, Extended feature mode disable, VLAN disable,	 LossLess flow control disable, Receive firmware statisic disable,	 Extended address parsing mode disable, One Rx queues,	 Dynamic maximum/minimum frame length disable, IP checksum check	 disable, IP address alignment disable	*/	out_be32(&uec->p_rx_glbl_pram->remoder, REMODER_INIT_VALUE);	/* RQPTR */	uec->thread_dat_rx_offset = qe_muram_alloc(			num_threads_rx * sizeof(uec_thread_data_rx_t),			 UEC_THREAD_DATA_ALIGNMENT);	uec->p_thread_data_rx = (uec_thread_data_rx_t *)				qe_muram_addr(uec->thread_dat_rx_offset);	out_be32(&uec->p_rx_glbl_pram->rqptr, uec->thread_dat_rx_offset);	/* Type_or_Len */	out_be16(&uec->p_rx_glbl_pram->typeorlen, 3072);	/* RxRMON base pointer, we don't need it */	out_be32(&uec->p_rx_glbl_pram->rxrmonbaseptr, 0);	/* IntCoalescingPTR, we don't need it, no interrupt */	out_be32(&uec->p_rx_glbl_pram->intcoalescingptr, 0);	/* RSTATE, global snooping, big endian, the CSB bus selected */	bmrx = BMR_INIT_VALUE;	out_8(&uec->p_rx_glbl_pram->rstate, bmrx);	/* MRBLR */	out_be16(&uec->p_rx_glbl_pram->mrblr, MAX_RXBUF_LEN);	/* RBDQPTR */	uec->rx_bd_qs_tbl_offset = qe_muram_alloc(				sizeof(uec_rx_bd_queues_entry_t) + \				sizeof(uec_rx_prefetched_bds_t),				 UEC_RX_BD_QUEUES_ALIGNMENT);	uec->p_rx_bd_qs_tbl = (uec_rx_bd_queues_entry_t *)				qe_muram_addr(uec->rx_bd_qs_tbl_offset);	/* Zero it */	memset(uec->p_rx_bd_qs_tbl, 0, sizeof(uec_rx_bd_queues_entry_t) + \					sizeof(uec_rx_prefetched_bds_t));	out_be32(&uec->p_rx_glbl_pram->rbdqptr, uec->rx_bd_qs_tbl_offset);	out_be32(&uec->p_rx_bd_qs_tbl->externalbdbaseptr,		 (u32)uec->p_rx_bd_ring);	/* MFLR */	out_be16(&uec->p_rx_glbl_pram->mflr, MAX_FRAME_LEN);	/* MINFLR */	out_be16(&uec->p_rx_glbl_pram->minflr, MIN_FRAME_LEN);	/* MAXD1 */	out_be16(&uec->p_rx_glbl_pram->maxd1, MAX_DMA1_LEN);	/* MAXD2 */	out_be16(&uec->p_rx_glbl_pram->maxd2, MAX_DMA2_LEN);	/* ECAM_PTR */	out_be32(&uec->p_rx_glbl_pram->ecamptr, 0);	/* L2QT */	out_be32(&uec->p_rx_glbl_pram->l2qt, 0);	/* L3QT */	for (i = 0; i < 8; i++)	{		out_be32(&uec->p_rx_glbl_pram->l3qt[i], 0);	}	/* VLAN_TYPE */	out_be16(&uec->p_rx_glbl_pram->vlantype, 0x8100);	/* TCI */	out_be16(&uec->p_rx_glbl_pram->vlantci, 0);	/* Clear PQ2 style address filtering hash table */	p_af_pram = (uec_82xx_address_filtering_pram_t *) \			uec->p_rx_glbl_pram->addressfiltering;	p_af_pram->iaddr_h = 0;	p_af_pram->iaddr_l = 0;	p_af_pram->gaddr_h = 0;	p_af_pram->gaddr_l = 0;}static int uec_issue_init_enet_rxtx_cmd(uec_private_t *uec,					 int thread_tx, int thread_rx){	uec_init_cmd_pram_t		*p_init_enet_param;	u32				init_enet_param_offset;	uec_info_t			*uec_info;	int				i;	int				snum;	u32				init_enet_offset;	u32				entry_val;	u32				command;	u32				cecr_subblock;	uec_info = uec->uec_info;	/* Allocate init enet command parameter */	uec->init_enet_param_offset = qe_muram_alloc(					sizeof(uec_init_cmd_pram_t), 4);	init_enet_param_offset = uec->init_enet_param_offset;	uec->p_init_enet_param = (uec_init_cmd_pram_t *)				qe_muram_addr(uec->init_enet_param_offset);	/* Zero init enet command struct */	memset((void *)uec->p_init_enet_param, 0, sizeof(uec_init_cmd_pram_t));	/* Init the command struct */	p_init_enet_param = uec->p_init_enet_param;	p_init_enet_param->resinit0 = ENET_INIT_PARAM_MAGIC_RES_INIT0;	p_init_enet_param->resinit1 = ENET_INIT_PARAM_MAGIC_RES_INIT1;	p_init_enet_param->resinit2 = ENET_INIT_PARAM_MAGIC_RES_INIT2;	p_init_enet_param->resinit3 = ENET_INIT_PARAM_MAGIC_RES_INIT3;	p_init_enet_param->resinit4 = ENET_INIT_PARAM_MAGIC_RES_INIT4;	p_init_enet_param->largestexternallookupkeysize = 0;	p_init_enet_param->rgftgfrxglobal |= ((u32)uec_info->num_threads_rx)					 << ENET_INIT_PARAM_RGF_SHIFT;	p_init_enet_param->rgftgfrxglobal |= ((u32)uec_info->num_threads_tx)					 << ENET_INIT_PARAM_TGF_SHIFT;	/* Init Rx global parameter pointer */	p_init_enet_param->rgftgfrxglobal |= uec->rx_glbl_pram_offset |						 (u32)uec_info->riscRx;	/* Init Rx threads */	for (i = 0; i < (thread_rx + 1); i++) {		if ((snum = qe_get_snum()) < 0) {			printf("%s can not get snum\n", __FUNCTION__);			return -ENOMEM;

⌨️ 快捷键说明

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