144961713Sgirish /* 244961713Sgirish * CDDL HEADER START 344961713Sgirish * 444961713Sgirish * The contents of this file are subject to the terms of the 544961713Sgirish * Common Development and Distribution License (the "License"). 644961713Sgirish * You may not use this file except in compliance with the License. 744961713Sgirish * 844961713Sgirish * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 944961713Sgirish * or http://www.opensolaris.org/os/licensing. 1044961713Sgirish * See the License for the specific language governing permissions 1144961713Sgirish * and limitations under the License. 1244961713Sgirish * 1344961713Sgirish * When distributing Covered Code, include this CDDL HEADER in each 1444961713Sgirish * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 1544961713Sgirish * If applicable, add the following below this CDDL HEADER, with the 1644961713Sgirish * fields enclosed by brackets "[]" replaced with your own identifying 1744961713Sgirish * information: Portions Copyright [yyyy] [name of copyright owner] 1844961713Sgirish * 1944961713Sgirish * CDDL HEADER END 2044961713Sgirish */ 2144961713Sgirish /* 22678453a8Sspeer * Copyright 2008 Sun Microsystems, Inc. All rights reserved. 2344961713Sgirish * Use is subject to license terms. 2444961713Sgirish */ 2544961713Sgirish 2644961713Sgirish #pragma ident "%Z%%M% %I% %E% SMI" 2744961713Sgirish 2844961713Sgirish #include <npi_fflp.h> 2944961713Sgirish #include <npi_mac.h> 3044961713Sgirish #include <nxge_defs.h> 3144961713Sgirish #include <nxge_flow.h> 3244961713Sgirish #include <nxge_fflp.h> 3344961713Sgirish #include <nxge_impl.h> 3444961713Sgirish #include <nxge_fflp_hash.h> 3544961713Sgirish #include <nxge_common.h> 3644961713Sgirish 3744961713Sgirish 38a3c5bd6dSspeer /* 39a3c5bd6dSspeer * Function prototypes 40a3c5bd6dSspeer */ 4144961713Sgirish static nxge_status_t nxge_fflp_vlan_tbl_clear_all(p_nxge_t); 4244961713Sgirish static nxge_status_t nxge_fflp_tcam_invalidate_all(p_nxge_t); 4344961713Sgirish static nxge_status_t nxge_fflp_tcam_init(p_nxge_t); 4444961713Sgirish static nxge_status_t nxge_fflp_fcram_invalidate_all(p_nxge_t); 4544961713Sgirish static nxge_status_t nxge_fflp_fcram_init(p_nxge_t); 4644961713Sgirish static int nxge_flow_need_hash_lookup(p_nxge_t, flow_resource_t *); 47a3c5bd6dSspeer static void nxge_fill_tcam_entry_tcp(p_nxge_t, flow_spec_t *, tcam_entry_t *); 48a3c5bd6dSspeer static void nxge_fill_tcam_entry_udp(p_nxge_t, flow_spec_t *, tcam_entry_t *); 49a3c5bd6dSspeer static void nxge_fill_tcam_entry_sctp(p_nxge_t, flow_spec_t *, tcam_entry_t *); 5044961713Sgirish static void nxge_fill_tcam_entry_tcp_ipv6(p_nxge_t, flow_spec_t *, 51a3c5bd6dSspeer tcam_entry_t *); 52a3c5bd6dSspeer static void nxge_fill_tcam_entry_udp_ipv6(p_nxge_t, flow_spec_t *, 53a3c5bd6dSspeer tcam_entry_t *); 54a3c5bd6dSspeer static void nxge_fill_tcam_entry_sctp_ipv6(p_nxge_t, flow_spec_t *, 55a3c5bd6dSspeer tcam_entry_t *); 5644961713Sgirish static uint8_t nxge_get_rdc_offset(p_nxge_t, uint8_t, intptr_t); 5744961713Sgirish static uint8_t nxge_get_rdc_group(p_nxge_t, uint8_t, intptr_t); 5844961713Sgirish static tcam_location_t nxge_get_tcam_location(p_nxge_t, uint8_t); 5944961713Sgirish 60a3c5bd6dSspeer /* 61a3c5bd6dSspeer * functions used outside this file 62a3c5bd6dSspeer */ 6344961713Sgirish nxge_status_t nxge_fflp_config_vlan_table(p_nxge_t, uint16_t); 6444961713Sgirish nxge_status_t nxge_fflp_ip_class_config_all(p_nxge_t); 6544961713Sgirish nxge_status_t nxge_add_flow(p_nxge_t, flow_resource_t *); 6614ea4bb7Ssd static nxge_status_t nxge_tcam_handle_ip_fragment(p_nxge_t); 6744961713Sgirish nxge_status_t nxge_add_tcam_entry(p_nxge_t, flow_resource_t *); 6844961713Sgirish nxge_status_t nxge_add_fcram_entry(p_nxge_t, flow_resource_t *); 6944961713Sgirish nxge_status_t nxge_flow_get_hash(p_nxge_t, flow_resource_t *, 70a3c5bd6dSspeer uint32_t *, uint16_t *); 7144961713Sgirish 7244961713Sgirish nxge_status_t 7344961713Sgirish nxge_tcam_dump_entry(p_nxge_t nxgep, uint32_t location) 7444961713Sgirish { 7544961713Sgirish tcam_entry_t tcam_rdptr; 7644961713Sgirish uint64_t asc_ram = 0; 7744961713Sgirish npi_handle_t handle; 7844961713Sgirish npi_status_t status; 7944961713Sgirish 8044961713Sgirish handle = nxgep->npi_reg_handle; 8144961713Sgirish 8244961713Sgirish bzero((char *)&tcam_rdptr, sizeof (struct tcam_entry)); 8344961713Sgirish status = npi_fflp_tcam_entry_read(handle, (tcam_location_t)location, 84*52ccf843Smisaki (struct tcam_entry *)&tcam_rdptr); 8544961713Sgirish if (status & NPI_FAILURE) { 8644961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 87*52ccf843Smisaki " nxge_tcam_dump_entry:" 88*52ccf843Smisaki " tcam read failed at location %d ", location)); 8944961713Sgirish return (NXGE_ERROR); 9044961713Sgirish } 9144961713Sgirish status = npi_fflp_tcam_asc_ram_entry_read(handle, 92*52ccf843Smisaki (tcam_location_t)location, &asc_ram); 9344961713Sgirish 9444961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, "location %x\n" 95*52ccf843Smisaki " key: %llx %llx %llx %llx \n" 96*52ccf843Smisaki " mask: %llx %llx %llx %llx \n" 97*52ccf843Smisaki " ASC RAM %llx \n", location, 98*52ccf843Smisaki tcam_rdptr.key0, tcam_rdptr.key1, 99*52ccf843Smisaki tcam_rdptr.key2, tcam_rdptr.key3, 100*52ccf843Smisaki tcam_rdptr.mask0, tcam_rdptr.mask1, 101*52ccf843Smisaki tcam_rdptr.mask2, tcam_rdptr.mask3, asc_ram)); 10244961713Sgirish return (NXGE_OK); 10344961713Sgirish } 10444961713Sgirish 10544961713Sgirish void 10644961713Sgirish nxge_get_tcam(p_nxge_t nxgep, p_mblk_t mp) 10744961713Sgirish { 10844961713Sgirish uint32_t tcam_loc; 10944961713Sgirish int *lptr; 11044961713Sgirish int location; 11144961713Sgirish 11244961713Sgirish uint32_t start_location = 0; 11344961713Sgirish uint32_t stop_location = nxgep->classifier.tcam_size; 11444961713Sgirish lptr = (int *)mp->b_rptr; 11544961713Sgirish location = *lptr; 11644961713Sgirish 11744961713Sgirish if ((location >= nxgep->classifier.tcam_size) || (location < -1)) { 11844961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 119*52ccf843Smisaki "nxge_tcam_dump: Invalid location %d \n", location)); 12044961713Sgirish return; 12144961713Sgirish } 12244961713Sgirish if (location == -1) { 12344961713Sgirish start_location = 0; 12444961713Sgirish stop_location = nxgep->classifier.tcam_size; 12544961713Sgirish } else { 12644961713Sgirish start_location = location; 127a3c5bd6dSspeer stop_location = location + 1; 12844961713Sgirish } 12944961713Sgirish for (tcam_loc = start_location; tcam_loc < stop_location; tcam_loc++) 13044961713Sgirish (void) nxge_tcam_dump_entry(nxgep, tcam_loc); 13144961713Sgirish } 13244961713Sgirish 13344961713Sgirish /* 13444961713Sgirish * nxge_fflp_vlan_table_invalidate_all 13544961713Sgirish * invalidates the vlan RDC table entries. 13644961713Sgirish * INPUT 13744961713Sgirish * nxge soft state data structure 13844961713Sgirish * Return 13944961713Sgirish * NXGE_OK 14044961713Sgirish * NXGE_ERROR 14144961713Sgirish * 14244961713Sgirish */ 143a3c5bd6dSspeer 14444961713Sgirish static nxge_status_t 14544961713Sgirish nxge_fflp_vlan_tbl_clear_all(p_nxge_t nxgep) 14644961713Sgirish { 14744961713Sgirish vlan_id_t vlan_id; 14844961713Sgirish npi_handle_t handle; 14944961713Sgirish npi_status_t rs = NPI_SUCCESS; 15044961713Sgirish vlan_id_t start = 0, stop = NXGE_MAX_VLANS; 15144961713Sgirish 15244961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "==> nxge_fflp_vlan_tbl_clear_all ")); 15344961713Sgirish handle = nxgep->npi_reg_handle; 15444961713Sgirish for (vlan_id = start; vlan_id < stop; vlan_id++) { 15544961713Sgirish rs = npi_fflp_cfg_vlan_table_clear(handle, vlan_id); 15644961713Sgirish if (rs != NPI_SUCCESS) { 15744961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 158*52ccf843Smisaki "VLAN Table invalidate failed for vlan id %d ", 159*52ccf843Smisaki vlan_id)); 16044961713Sgirish return (NXGE_ERROR | rs); 16144961713Sgirish } 16244961713Sgirish } 16344961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "<== nxge_fflp_vlan_tbl_clear_all ")); 16444961713Sgirish return (NXGE_OK); 16544961713Sgirish } 16644961713Sgirish 16744961713Sgirish /* 16844961713Sgirish * The following functions are used by other modules to init 16944961713Sgirish * the fflp module. 17044961713Sgirish * these functions are the basic API used to init 17144961713Sgirish * the fflp modules (tcam, fcram etc ......) 17244961713Sgirish * 17344961713Sgirish * The TCAM search future would be disabled by default. 17444961713Sgirish */ 17544961713Sgirish 17644961713Sgirish static nxge_status_t 17744961713Sgirish nxge_fflp_tcam_init(p_nxge_t nxgep) 17844961713Sgirish { 17944961713Sgirish uint8_t access_ratio; 18044961713Sgirish tcam_class_t class; 18144961713Sgirish npi_status_t rs = NPI_SUCCESS; 18244961713Sgirish npi_handle_t handle; 18344961713Sgirish 18444961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "==> nxge_fflp_tcam_init")); 18544961713Sgirish handle = nxgep->npi_reg_handle; 18644961713Sgirish 18744961713Sgirish rs = npi_fflp_cfg_tcam_disable(handle); 18844961713Sgirish if (rs != NPI_SUCCESS) { 18944961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, "failed TCAM Disable\n")); 19044961713Sgirish return (NXGE_ERROR | rs); 19144961713Sgirish } 19244961713Sgirish 19344961713Sgirish access_ratio = nxgep->param_arr[param_tcam_access_ratio].value; 19444961713Sgirish rs = npi_fflp_cfg_tcam_access(handle, access_ratio); 19544961713Sgirish if (rs != NPI_SUCCESS) { 19644961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 197*52ccf843Smisaki "failed TCAM Access cfg\n")); 19844961713Sgirish return (NXGE_ERROR | rs); 19944961713Sgirish } 20044961713Sgirish 201a3c5bd6dSspeer /* disable configurable classes */ 202a3c5bd6dSspeer /* disable the configurable ethernet classes; */ 20344961713Sgirish for (class = TCAM_CLASS_ETYPE_1; 204*52ccf843Smisaki class <= TCAM_CLASS_ETYPE_2; class++) { 20544961713Sgirish rs = npi_fflp_cfg_enet_usr_cls_disable(handle, class); 20644961713Sgirish if (rs != NPI_SUCCESS) { 20744961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 208*52ccf843Smisaki "TCAM USR Ether Class config failed.")); 20944961713Sgirish return (NXGE_ERROR | rs); 21044961713Sgirish } 21144961713Sgirish } 21244961713Sgirish 213a3c5bd6dSspeer /* disable the configurable ip classes; */ 21444961713Sgirish for (class = TCAM_CLASS_IP_USER_4; 215*52ccf843Smisaki class <= TCAM_CLASS_IP_USER_7; class++) { 21644961713Sgirish rs = npi_fflp_cfg_ip_usr_cls_disable(handle, class); 21744961713Sgirish if (rs != NPI_SUCCESS) { 21844961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 219*52ccf843Smisaki "TCAM USR IP Class cnfg failed.")); 22044961713Sgirish return (NXGE_ERROR | rs); 22144961713Sgirish } 22244961713Sgirish } 22344961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "<== nxge_fflp_tcam_init")); 22444961713Sgirish return (NXGE_OK); 22544961713Sgirish } 22644961713Sgirish 22744961713Sgirish /* 22844961713Sgirish * nxge_fflp_tcam_invalidate_all 22944961713Sgirish * invalidates all the tcam entries. 23044961713Sgirish * INPUT 23144961713Sgirish * nxge soft state data structure 23244961713Sgirish * Return 23344961713Sgirish * NXGE_OK 23444961713Sgirish * NXGE_ERROR 23544961713Sgirish * 23644961713Sgirish */ 237a3c5bd6dSspeer 238a3c5bd6dSspeer 23944961713Sgirish static nxge_status_t 24044961713Sgirish nxge_fflp_tcam_invalidate_all(p_nxge_t nxgep) 24144961713Sgirish { 24244961713Sgirish uint16_t location; 24344961713Sgirish npi_status_t rs = NPI_SUCCESS; 24444961713Sgirish npi_handle_t handle; 24544961713Sgirish uint16_t start = 0, stop = nxgep->classifier.tcam_size; 246a3c5bd6dSspeer p_nxge_hw_list_t hw_p; 24744961713Sgirish 24844961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 249*52ccf843Smisaki "==> nxge_fflp_tcam_invalidate_all")); 25044961713Sgirish handle = nxgep->npi_reg_handle; 25144961713Sgirish if ((hw_p = nxgep->nxge_hw_p) == NULL) { 25244961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 253*52ccf843Smisaki " nxge_fflp_tcam_invalidate_all:" 254*52ccf843Smisaki " common hardware not set", nxgep->niu_type)); 25544961713Sgirish return (NXGE_ERROR); 25644961713Sgirish } 25744961713Sgirish MUTEX_ENTER(&hw_p->nxge_tcam_lock); 25844961713Sgirish for (location = start; location < stop; location++) { 25944961713Sgirish rs = npi_fflp_tcam_entry_invalidate(handle, location); 26044961713Sgirish if (rs != NPI_SUCCESS) { 26144961713Sgirish MUTEX_EXIT(&hw_p->nxge_tcam_lock); 26244961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 263*52ccf843Smisaki "TCAM invalidate failed at loc %d ", location)); 26444961713Sgirish return (NXGE_ERROR | rs); 26544961713Sgirish } 26644961713Sgirish } 26744961713Sgirish MUTEX_EXIT(&hw_p->nxge_tcam_lock); 26844961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 269*52ccf843Smisaki "<== nxge_fflp_tcam_invalidate_all")); 27044961713Sgirish return (NXGE_OK); 27144961713Sgirish } 27244961713Sgirish 27344961713Sgirish /* 27444961713Sgirish * nxge_fflp_fcram_entry_invalidate_all 27544961713Sgirish * invalidates all the FCRAM entries. 27644961713Sgirish * INPUT 27744961713Sgirish * nxge soft state data structure 27844961713Sgirish * Return 27944961713Sgirish * NXGE_OK 28044961713Sgirish * NXGE_ERROR 28144961713Sgirish * 28244961713Sgirish */ 283a3c5bd6dSspeer 28444961713Sgirish static nxge_status_t 28544961713Sgirish nxge_fflp_fcram_invalidate_all(p_nxge_t nxgep) 28644961713Sgirish { 287a3c5bd6dSspeer npi_handle_t handle; 288a3c5bd6dSspeer npi_status_t rs = NPI_SUCCESS; 289a3c5bd6dSspeer part_id_t pid = 0; 290a3c5bd6dSspeer uint8_t base_mask, base_reloc; 291a3c5bd6dSspeer fcram_entry_t fc; 292a3c5bd6dSspeer uint32_t location; 293a3c5bd6dSspeer uint32_t increment, last_location; 29444961713Sgirish 295a3c5bd6dSspeer /* 296a3c5bd6dSspeer * (1) configure and enable partition 0 with no relocation 297a3c5bd6dSspeer * (2) Assume the FCRAM is used as IPv4 exact match entry cells 298a3c5bd6dSspeer * (3) Invalidate these cells by clearing the valid bit in 299a3c5bd6dSspeer * the subareas 0 and 4 300a3c5bd6dSspeer * (4) disable the partition 301a3c5bd6dSspeer * 302a3c5bd6dSspeer */ 30344961713Sgirish 30444961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "==> nxge_fflp_fcram_invalidate_all")); 30544961713Sgirish 30644961713Sgirish base_mask = base_reloc = 0x0; 30744961713Sgirish handle = nxgep->npi_reg_handle; 308a3c5bd6dSspeer rs = npi_fflp_cfg_fcram_partition(handle, pid, base_mask, base_reloc); 30944961713Sgirish 31044961713Sgirish if (rs != NPI_SUCCESS) { 311a3c5bd6dSspeer NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, "failed partition cfg\n")); 31244961713Sgirish return (NXGE_ERROR | rs); 31344961713Sgirish } 314a3c5bd6dSspeer rs = npi_fflp_cfg_fcram_partition_disable(handle, pid); 31544961713Sgirish 31644961713Sgirish if (rs != NPI_SUCCESS) { 31744961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 318*52ccf843Smisaki "failed partition enable\n")); 31944961713Sgirish return (NXGE_ERROR | rs); 32044961713Sgirish } 321a3c5bd6dSspeer fc.dreg[0].value = 0; 322a3c5bd6dSspeer fc.hash_hdr_valid = 0; 323a3c5bd6dSspeer fc.hash_hdr_ext = 1; /* specify as IPV4 exact match entry */ 324a3c5bd6dSspeer increment = sizeof (hash_ipv4_t); 325a3c5bd6dSspeer last_location = FCRAM_SIZE * 0x40; 32644961713Sgirish 327a3c5bd6dSspeer for (location = 0; location < last_location; location += increment) { 32844961713Sgirish rs = npi_fflp_fcram_subarea_write(handle, pid, 329*52ccf843Smisaki location, fc.value[0]); 33044961713Sgirish if (rs != NPI_SUCCESS) { 33144961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 332*52ccf843Smisaki "failed write at location %x ", location)); 33344961713Sgirish return (NXGE_ERROR | rs); 33444961713Sgirish } 33544961713Sgirish } 33644961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "<== nxge_fflp_fcram_invalidate_all")); 337a3c5bd6dSspeer return (NXGE_OK); 33844961713Sgirish } 33944961713Sgirish 34044961713Sgirish static nxge_status_t 34144961713Sgirish nxge_fflp_fcram_init(p_nxge_t nxgep) 34244961713Sgirish { 34344961713Sgirish fflp_fcram_output_drive_t strength; 34444961713Sgirish fflp_fcram_qs_t qs; 34544961713Sgirish npi_status_t rs = NPI_SUCCESS; 34644961713Sgirish uint8_t access_ratio; 347a3c5bd6dSspeer int partition; 34844961713Sgirish npi_handle_t handle; 349a3c5bd6dSspeer uint32_t min_time, max_time, sys_time; 35044961713Sgirish 35144961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "==> nxge_fflp_fcram_init")); 35244961713Sgirish 353a3c5bd6dSspeer /* 354a3c5bd6dSspeer * Recommended values are needed. 355a3c5bd6dSspeer */ 35644961713Sgirish min_time = FCRAM_REFRESH_DEFAULT_MIN_TIME; 35744961713Sgirish max_time = FCRAM_REFRESH_DEFAULT_MAX_TIME; 35844961713Sgirish sys_time = FCRAM_REFRESH_DEFAULT_SYS_TIME; 359a3c5bd6dSspeer 36044961713Sgirish handle = nxgep->npi_reg_handle; 36144961713Sgirish strength = FCRAM_OUTDR_NORMAL; 36244961713Sgirish qs = FCRAM_QS_MODE_QS; 36344961713Sgirish rs = npi_fflp_cfg_fcram_reset(handle, strength, qs); 36444961713Sgirish if (rs != NPI_SUCCESS) { 36544961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, "failed FCRAM Reset. ")); 36644961713Sgirish return (NXGE_ERROR | rs); 36744961713Sgirish } 36844961713Sgirish 369a3c5bd6dSspeer access_ratio = nxgep->param_arr[param_fcram_access_ratio].value; 370a3c5bd6dSspeer rs = npi_fflp_cfg_fcram_access(handle, access_ratio); 371a3c5bd6dSspeer if (rs != NPI_SUCCESS) { 37244961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, "failed FCRAM Access ratio" 373*52ccf843Smisaki "configuration \n")); 37444961713Sgirish return (NXGE_ERROR | rs); 37544961713Sgirish } 37644961713Sgirish rs = npi_fflp_cfg_fcram_refresh_time(handle, min_time, 377*52ccf843Smisaki max_time, sys_time); 37844961713Sgirish if (rs != NPI_SUCCESS) { 37944961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 380*52ccf843Smisaki "failed FCRAM refresh cfg")); 38144961713Sgirish return (NXGE_ERROR); 38244961713Sgirish } 38344961713Sgirish 38444961713Sgirish /* disable all the partitions until explicitly enabled */ 38544961713Sgirish for (partition = 0; partition < FFLP_FCRAM_MAX_PARTITION; partition++) { 386a3c5bd6dSspeer rs = npi_fflp_cfg_fcram_partition_disable(handle, partition); 38744961713Sgirish if (rs != NPI_SUCCESS) { 38844961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 389*52ccf843Smisaki "failed FCRAM partition" 390*52ccf843Smisaki " enable for partition %d ", partition)); 39144961713Sgirish return (NXGE_ERROR | rs); 39244961713Sgirish } 39344961713Sgirish } 39444961713Sgirish 39544961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "<== nxge_fflp_fcram_init")); 396a3c5bd6dSspeer return (NXGE_OK); 39744961713Sgirish } 39844961713Sgirish 39944961713Sgirish nxge_status_t 40044961713Sgirish nxge_logical_mac_assign_rdc_table(p_nxge_t nxgep, uint8_t alt_mac) 40144961713Sgirish { 40244961713Sgirish npi_status_t rs = NPI_SUCCESS; 40344961713Sgirish hostinfo_t mac_rdc; 40444961713Sgirish npi_handle_t handle; 405a3c5bd6dSspeer p_nxge_class_pt_cfg_t p_class_cfgp; 40644961713Sgirish 407a3c5bd6dSspeer p_class_cfgp = (p_nxge_class_pt_cfg_t)&nxgep->class_config; 40844961713Sgirish if (p_class_cfgp->mac_host_info[alt_mac].flag == 0) { 409a3c5bd6dSspeer NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 410*52ccf843Smisaki " nxge_logical_mac_assign_rdc_table" 411*52ccf843Smisaki " unconfigured alt MAC addr %d ", alt_mac)); 41244961713Sgirish return (NXGE_ERROR); 41344961713Sgirish } 41444961713Sgirish handle = nxgep->npi_reg_handle; 41544961713Sgirish mac_rdc.value = 0; 41644961713Sgirish mac_rdc.bits.w0.rdc_tbl_num = 417*52ccf843Smisaki p_class_cfgp->mac_host_info[alt_mac].rdctbl; 41844961713Sgirish mac_rdc.bits.w0.mac_pref = p_class_cfgp->mac_host_info[alt_mac].mpr_npr; 41944961713Sgirish 42044961713Sgirish rs = npi_mac_hostinfo_entry(handle, OP_SET, 421*52ccf843Smisaki nxgep->function_num, alt_mac, &mac_rdc); 42244961713Sgirish 42344961713Sgirish if (rs != NPI_SUCCESS) { 42444961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 425*52ccf843Smisaki "failed Assign RDC table")); 42644961713Sgirish return (NXGE_ERROR | rs); 42744961713Sgirish } 42844961713Sgirish return (NXGE_OK); 42944961713Sgirish } 43044961713Sgirish 43144961713Sgirish nxge_status_t 43244961713Sgirish nxge_main_mac_assign_rdc_table(p_nxge_t nxgep) 43344961713Sgirish { 43444961713Sgirish npi_status_t rs = NPI_SUCCESS; 43544961713Sgirish hostinfo_t mac_rdc; 43644961713Sgirish npi_handle_t handle; 43744961713Sgirish 43844961713Sgirish handle = nxgep->npi_reg_handle; 43944961713Sgirish mac_rdc.value = 0; 44044961713Sgirish mac_rdc.bits.w0.rdc_tbl_num = nxgep->class_config.mac_rdcgrp; 44144961713Sgirish mac_rdc.bits.w0.mac_pref = 1; 44244961713Sgirish switch (nxgep->function_num) { 443a3c5bd6dSspeer case 0: 444a3c5bd6dSspeer case 1: 445a3c5bd6dSspeer rs = npi_mac_hostinfo_entry(handle, OP_SET, 446*52ccf843Smisaki nxgep->function_num, XMAC_UNIQUE_HOST_INFO_ENTRY, &mac_rdc); 447a3c5bd6dSspeer break; 448a3c5bd6dSspeer case 2: 449a3c5bd6dSspeer case 3: 450a3c5bd6dSspeer rs = npi_mac_hostinfo_entry(handle, OP_SET, 451*52ccf843Smisaki nxgep->function_num, BMAC_UNIQUE_HOST_INFO_ENTRY, &mac_rdc); 452a3c5bd6dSspeer break; 453a3c5bd6dSspeer default: 454a3c5bd6dSspeer NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 455*52ccf843Smisaki "failed Assign RDC table (invalid function #)")); 456a3c5bd6dSspeer return (NXGE_ERROR); 45744961713Sgirish } 45844961713Sgirish 45944961713Sgirish if (rs != NPI_SUCCESS) { 46044961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 461*52ccf843Smisaki "failed Assign RDC table")); 46244961713Sgirish return (NXGE_ERROR | rs); 46344961713Sgirish } 46444961713Sgirish return (NXGE_OK); 46544961713Sgirish } 46644961713Sgirish 46758324dfcSspeer /* 46858324dfcSspeer * Initialize hostinfo registers for alternate MAC addresses and 46958324dfcSspeer * multicast MAC address. 47058324dfcSspeer */ 47144961713Sgirish nxge_status_t 47258324dfcSspeer nxge_alt_mcast_mac_assign_rdc_table(p_nxge_t nxgep) 47344961713Sgirish { 47444961713Sgirish npi_status_t rs = NPI_SUCCESS; 47544961713Sgirish hostinfo_t mac_rdc; 47644961713Sgirish npi_handle_t handle; 47758324dfcSspeer int i; 47844961713Sgirish 47944961713Sgirish handle = nxgep->npi_reg_handle; 48044961713Sgirish mac_rdc.value = 0; 48144961713Sgirish mac_rdc.bits.w0.rdc_tbl_num = nxgep->class_config.mcast_rdcgrp; 48244961713Sgirish mac_rdc.bits.w0.mac_pref = 1; 48344961713Sgirish switch (nxgep->function_num) { 484a3c5bd6dSspeer case 0: 485a3c5bd6dSspeer case 1: 48658324dfcSspeer /* 48758324dfcSspeer * Tests indicate that it is OK not to re-initialize the 48858324dfcSspeer * hostinfo registers for the XMAC's alternate MAC 48958324dfcSspeer * addresses. But that is necessary for BMAC (case 2 49058324dfcSspeer * and case 3 below) 49158324dfcSspeer */ 492a3c5bd6dSspeer rs = npi_mac_hostinfo_entry(handle, OP_SET, 493*52ccf843Smisaki nxgep->function_num, 494*52ccf843Smisaki XMAC_MULTI_HOST_INFO_ENTRY, &mac_rdc); 495a3c5bd6dSspeer break; 496a3c5bd6dSspeer case 2: 497a3c5bd6dSspeer case 3: 49858324dfcSspeer for (i = 1; i <= BMAC_MAX_ALT_ADDR_ENTRY; i++) 49958324dfcSspeer rs |= npi_mac_hostinfo_entry(handle, OP_SET, 500*52ccf843Smisaki nxgep->function_num, i, &mac_rdc); 50158324dfcSspeer 50258324dfcSspeer rs |= npi_mac_hostinfo_entry(handle, OP_SET, 503*52ccf843Smisaki nxgep->function_num, 504*52ccf843Smisaki BMAC_MULTI_HOST_INFO_ENTRY, &mac_rdc); 505a3c5bd6dSspeer break; 506a3c5bd6dSspeer default: 507a3c5bd6dSspeer NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 508*52ccf843Smisaki "failed Assign RDC table (invalid function #)")); 509a3c5bd6dSspeer return (NXGE_ERROR); 51044961713Sgirish } 51144961713Sgirish 51244961713Sgirish if (rs != NPI_SUCCESS) { 51344961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 514*52ccf843Smisaki "failed Assign RDC table")); 51544961713Sgirish return (NXGE_ERROR | rs); 51644961713Sgirish } 51744961713Sgirish return (NXGE_OK); 51844961713Sgirish } 51944961713Sgirish 52044961713Sgirish nxge_status_t 52144961713Sgirish nxge_fflp_init_hostinfo(p_nxge_t nxgep) 52244961713Sgirish { 52344961713Sgirish nxge_status_t status = NXGE_OK; 524a3c5bd6dSspeer 52558324dfcSspeer status = nxge_alt_mcast_mac_assign_rdc_table(nxgep); 52658324dfcSspeer status |= nxge_main_mac_assign_rdc_table(nxgep); 52744961713Sgirish return (status); 52844961713Sgirish } 52944961713Sgirish 53044961713Sgirish nxge_status_t 53144961713Sgirish nxge_fflp_hw_reset(p_nxge_t nxgep) 53244961713Sgirish { 53344961713Sgirish npi_handle_t handle; 53444961713Sgirish npi_status_t rs = NPI_SUCCESS; 53544961713Sgirish nxge_status_t status = NXGE_OK; 53644961713Sgirish 53744961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, " ==> nxge_fflp_hw_reset")); 53844961713Sgirish 5392e59129aSraghus if (NXGE_IS_VALID_NEPTUNE_TYPE(nxgep)) { 54044961713Sgirish status = nxge_fflp_fcram_init(nxgep); 541a3c5bd6dSspeer if (status != NXGE_OK) { 54244961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 543*52ccf843Smisaki " failed FCRAM init. ")); 54444961713Sgirish return (status); 54544961713Sgirish } 54644961713Sgirish } 54744961713Sgirish 54844961713Sgirish status = nxge_fflp_tcam_init(nxgep); 54944961713Sgirish if (status != NXGE_OK) { 550a3c5bd6dSspeer NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 551*52ccf843Smisaki "failed TCAM init.")); 552a3c5bd6dSspeer return (status); 55344961713Sgirish } 55444961713Sgirish 55544961713Sgirish handle = nxgep->npi_reg_handle; 55644961713Sgirish rs = npi_fflp_cfg_llcsnap_enable(handle); 55744961713Sgirish if (rs != NPI_SUCCESS) { 558a3c5bd6dSspeer NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 559*52ccf843Smisaki "failed LLCSNAP enable. ")); 560a3c5bd6dSspeer return (NXGE_ERROR | rs); 56144961713Sgirish } 56244961713Sgirish 56344961713Sgirish rs = npi_fflp_cfg_cam_errorcheck_disable(handle); 56444961713Sgirish if (rs != NPI_SUCCESS) { 56544961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 566*52ccf843Smisaki "failed CAM Error Check enable. ")); 56744961713Sgirish return (NXGE_ERROR | rs); 56844961713Sgirish } 56944961713Sgirish 570a3c5bd6dSspeer /* init the hash generators */ 57144961713Sgirish rs = npi_fflp_cfg_hash_h1poly(handle, 0); 57244961713Sgirish if (rs != NPI_SUCCESS) { 573a3c5bd6dSspeer NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 574*52ccf843Smisaki "failed H1 Poly Init. ")); 575a3c5bd6dSspeer return (NXGE_ERROR | rs); 57644961713Sgirish } 57744961713Sgirish 57844961713Sgirish rs = npi_fflp_cfg_hash_h2poly(handle, 0); 57944961713Sgirish if (rs != NPI_SUCCESS) { 580a3c5bd6dSspeer NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 581*52ccf843Smisaki "failed H2 Poly Init. ")); 582a3c5bd6dSspeer return (NXGE_ERROR | rs); 58344961713Sgirish } 58444961713Sgirish 585a3c5bd6dSspeer /* invalidate TCAM entries */ 58644961713Sgirish status = nxge_fflp_tcam_invalidate_all(nxgep); 58744961713Sgirish if (status != NXGE_OK) { 58844961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 589*52ccf843Smisaki "failed TCAM Entry Invalidate. ")); 59044961713Sgirish return (status); 59144961713Sgirish } 59244961713Sgirish 593a3c5bd6dSspeer /* invalidate FCRAM entries */ 5942e59129aSraghus if (NXGE_IS_VALID_NEPTUNE_TYPE(nxgep)) { 59544961713Sgirish status = nxge_fflp_fcram_invalidate_all(nxgep); 59644961713Sgirish if (status != NXGE_OK) { 59744961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 598*52ccf843Smisaki "failed FCRAM Entry Invalidate.")); 59944961713Sgirish return (status); 60044961713Sgirish } 60144961713Sgirish } 60244961713Sgirish 603a3c5bd6dSspeer /* invalidate VLAN RDC tables */ 60444961713Sgirish status = nxge_fflp_vlan_tbl_clear_all(nxgep); 60544961713Sgirish if (status != NXGE_OK) { 60644961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 607*52ccf843Smisaki "failed VLAN Table Invalidate. ")); 60844961713Sgirish return (status); 60944961713Sgirish } 61044961713Sgirish nxgep->classifier.state |= NXGE_FFLP_HW_RESET; 61144961713Sgirish 61244961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "<== nxge_fflp_hw_reset")); 61344961713Sgirish return (NXGE_OK); 61444961713Sgirish } 61544961713Sgirish 61644961713Sgirish nxge_status_t 61744961713Sgirish nxge_cfg_ip_cls_flow_key(p_nxge_t nxgep, tcam_class_t l3_class, 618a3c5bd6dSspeer uint32_t class_config) 61944961713Sgirish { 62044961713Sgirish flow_key_cfg_t fcfg; 62144961713Sgirish npi_handle_t handle; 62244961713Sgirish npi_status_t rs = NPI_SUCCESS; 62344961713Sgirish 62444961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, " ==> nxge_cfg_ip_cls_flow_key")); 62544961713Sgirish handle = nxgep->npi_reg_handle; 62644961713Sgirish bzero(&fcfg, sizeof (flow_key_cfg_t)); 62744961713Sgirish 628a3c5bd6dSspeer if (class_config & NXGE_CLASS_FLOW_USE_PROTO) 62944961713Sgirish fcfg.use_proto = 1; 63044961713Sgirish if (class_config & NXGE_CLASS_FLOW_USE_DST_PORT) 63144961713Sgirish fcfg.use_dport = 1; 63244961713Sgirish if (class_config & NXGE_CLASS_FLOW_USE_SRC_PORT) 63344961713Sgirish fcfg.use_sport = 1; 63444961713Sgirish if (class_config & NXGE_CLASS_FLOW_USE_IPDST) 63544961713Sgirish fcfg.use_daddr = 1; 63644961713Sgirish if (class_config & NXGE_CLASS_FLOW_USE_IPSRC) 63744961713Sgirish fcfg.use_saddr = 1; 63844961713Sgirish if (class_config & NXGE_CLASS_FLOW_USE_VLAN) 63944961713Sgirish fcfg.use_vlan = 1; 64044961713Sgirish if (class_config & NXGE_CLASS_FLOW_USE_L2DA) 64144961713Sgirish fcfg.use_l2da = 1; 64244961713Sgirish if (class_config & NXGE_CLASS_FLOW_USE_PORTNUM) 64344961713Sgirish fcfg.use_portnum = 1; 64444961713Sgirish fcfg.ip_opts_exist = 0; 64544961713Sgirish 64644961713Sgirish rs = npi_fflp_cfg_ip_cls_flow_key(handle, l3_class, &fcfg); 64744961713Sgirish if (rs & NPI_FFLP_ERROR) { 64844961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, " nxge_cfg_ip_cls_flow_key" 649*52ccf843Smisaki " opt %x for class %d failed ", class_config, l3_class)); 65044961713Sgirish return (NXGE_ERROR | rs); 65144961713Sgirish } 65244961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, " <== nxge_cfg_ip_cls_flow_key")); 65344961713Sgirish return (NXGE_OK); 65444961713Sgirish } 65544961713Sgirish 65644961713Sgirish nxge_status_t 65744961713Sgirish nxge_cfg_ip_cls_flow_key_get(p_nxge_t nxgep, tcam_class_t l3_class, 658a3c5bd6dSspeer uint32_t *class_config) 65944961713Sgirish { 66044961713Sgirish flow_key_cfg_t fcfg; 66144961713Sgirish npi_handle_t handle; 66244961713Sgirish npi_status_t rs = NPI_SUCCESS; 66344961713Sgirish uint32_t ccfg = 0; 664a3c5bd6dSspeer 66544961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, " ==> nxge_cfg_ip_cls_flow_key_get")); 66644961713Sgirish handle = nxgep->npi_reg_handle; 66744961713Sgirish bzero(&fcfg, sizeof (flow_key_cfg_t)); 66844961713Sgirish 66944961713Sgirish rs = npi_fflp_cfg_ip_cls_flow_key_get(handle, l3_class, &fcfg); 67044961713Sgirish if (rs & NPI_FFLP_ERROR) { 67144961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, " nxge_cfg_ip_cls_flow_key" 672*52ccf843Smisaki " opt %x for class %d failed ", class_config, l3_class)); 67344961713Sgirish return (NXGE_ERROR | rs); 67444961713Sgirish } 67544961713Sgirish 67644961713Sgirish if (fcfg.use_proto) 67744961713Sgirish ccfg |= NXGE_CLASS_FLOW_USE_PROTO; 67844961713Sgirish if (fcfg.use_dport) 67944961713Sgirish ccfg |= NXGE_CLASS_FLOW_USE_DST_PORT; 68044961713Sgirish if (fcfg.use_sport) 68144961713Sgirish ccfg |= NXGE_CLASS_FLOW_USE_SRC_PORT; 68244961713Sgirish if (fcfg.use_daddr) 68344961713Sgirish ccfg |= NXGE_CLASS_FLOW_USE_IPDST; 68444961713Sgirish if (fcfg.use_saddr) 68544961713Sgirish ccfg |= NXGE_CLASS_FLOW_USE_IPSRC; 68644961713Sgirish if (fcfg.use_vlan) 68744961713Sgirish ccfg |= NXGE_CLASS_FLOW_USE_VLAN; 68844961713Sgirish if (fcfg.use_l2da) 68944961713Sgirish ccfg |= NXGE_CLASS_FLOW_USE_L2DA; 69044961713Sgirish if (fcfg.use_portnum) 691a3c5bd6dSspeer ccfg |= NXGE_CLASS_FLOW_USE_PORTNUM; 69244961713Sgirish 69344961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 694*52ccf843Smisaki " nxge_cfg_ip_cls_flow_key_get %x", ccfg)); 69544961713Sgirish *class_config = ccfg; 69644961713Sgirish 69744961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 698*52ccf843Smisaki " <== nxge_cfg_ip_cls_flow_key_get")); 69944961713Sgirish return (NXGE_OK); 70044961713Sgirish } 70144961713Sgirish 70244961713Sgirish static nxge_status_t 70344961713Sgirish nxge_cfg_tcam_ip_class_get(p_nxge_t nxgep, tcam_class_t class, 704a3c5bd6dSspeer uint32_t *class_config) 70544961713Sgirish { 70644961713Sgirish npi_status_t rs = NPI_SUCCESS; 70744961713Sgirish tcam_key_cfg_t cfg; 70844961713Sgirish npi_handle_t handle; 70944961713Sgirish uint32_t ccfg = 0; 71044961713Sgirish 71144961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "==> nxge_cfg_tcam_ip_class")); 71244961713Sgirish 71344961713Sgirish bzero(&cfg, sizeof (tcam_key_cfg_t)); 71444961713Sgirish handle = nxgep->npi_reg_handle; 71544961713Sgirish 71644961713Sgirish rs = npi_fflp_cfg_ip_cls_tcam_key_get(handle, class, &cfg); 71744961713Sgirish if (rs & NPI_FFLP_ERROR) { 71844961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, " nxge_cfg_tcam_ip_class" 719*52ccf843Smisaki " opt %x for class %d failed ", class_config, class)); 72044961713Sgirish return (NXGE_ERROR | rs); 72144961713Sgirish } 72244961713Sgirish if (cfg.discard) 723a3c5bd6dSspeer ccfg |= NXGE_CLASS_DISCARD; 72444961713Sgirish if (cfg.lookup_enable) 72544961713Sgirish ccfg |= NXGE_CLASS_TCAM_LOOKUP; 72644961713Sgirish if (cfg.use_ip_daddr) 727a3c5bd6dSspeer ccfg |= NXGE_CLASS_TCAM_USE_SRC_ADDR; 72844961713Sgirish *class_config = ccfg; 72944961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 730*52ccf843Smisaki " ==> nxge_cfg_tcam_ip_class %x", ccfg)); 73144961713Sgirish return (NXGE_OK); 73244961713Sgirish } 73344961713Sgirish 73444961713Sgirish static nxge_status_t 73544961713Sgirish nxge_cfg_tcam_ip_class(p_nxge_t nxgep, tcam_class_t class, 736a3c5bd6dSspeer uint32_t class_config) 73744961713Sgirish { 73844961713Sgirish npi_status_t rs = NPI_SUCCESS; 73944961713Sgirish tcam_key_cfg_t cfg; 74044961713Sgirish npi_handle_t handle; 741a3c5bd6dSspeer p_nxge_class_pt_cfg_t p_class_cfgp; 74244961713Sgirish 74344961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "==> nxge_cfg_tcam_ip_class")); 744a3c5bd6dSspeer 74544961713Sgirish p_class_cfgp = (p_nxge_class_pt_cfg_t)&nxgep->class_config; 74644961713Sgirish p_class_cfgp->class_cfg[class] = class_config; 74744961713Sgirish 74844961713Sgirish bzero(&cfg, sizeof (tcam_key_cfg_t)); 74944961713Sgirish handle = nxgep->npi_reg_handle; 75044961713Sgirish cfg.discard = 0; 75144961713Sgirish cfg.lookup_enable = 0; 75244961713Sgirish cfg.use_ip_daddr = 0; 75344961713Sgirish if (class_config & NXGE_CLASS_DISCARD) 75444961713Sgirish cfg.discard = 1; 75544961713Sgirish if (class_config & NXGE_CLASS_TCAM_LOOKUP) 75644961713Sgirish cfg.lookup_enable = 1; 757a3c5bd6dSspeer if (class_config & NXGE_CLASS_TCAM_USE_SRC_ADDR) 75844961713Sgirish cfg.use_ip_daddr = 1; 75944961713Sgirish 76044961713Sgirish rs = npi_fflp_cfg_ip_cls_tcam_key(handle, class, &cfg); 76144961713Sgirish if (rs & NPI_FFLP_ERROR) { 76244961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, " nxge_cfg_tcam_ip_class" 763*52ccf843Smisaki " opt %x for class %d failed ", class_config, class)); 76444961713Sgirish return (NXGE_ERROR | rs); 76544961713Sgirish } 76644961713Sgirish return (NXGE_OK); 76744961713Sgirish } 76844961713Sgirish 76944961713Sgirish nxge_status_t 77044961713Sgirish nxge_fflp_set_hash1(p_nxge_t nxgep, uint32_t h1) 77144961713Sgirish { 77244961713Sgirish npi_status_t rs = NPI_SUCCESS; 77344961713Sgirish npi_handle_t handle; 774a3c5bd6dSspeer p_nxge_class_pt_cfg_t p_class_cfgp; 77544961713Sgirish 77644961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, " ==> nxge_fflp_init_h1")); 77744961713Sgirish p_class_cfgp = (p_nxge_class_pt_cfg_t)&nxgep->class_config; 77844961713Sgirish p_class_cfgp->init_h1 = h1; 77944961713Sgirish handle = nxgep->npi_reg_handle; 78044961713Sgirish rs = npi_fflp_cfg_hash_h1poly(handle, h1); 78144961713Sgirish if (rs & NPI_FFLP_ERROR) { 782a3c5bd6dSspeer NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 783*52ccf843Smisaki " nxge_fflp_init_h1 %x failed ", h1)); 78444961713Sgirish return (NXGE_ERROR | rs); 78544961713Sgirish } 78644961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, " <== nxge_fflp_init_h1")); 78744961713Sgirish return (NXGE_OK); 78844961713Sgirish } 78944961713Sgirish 79044961713Sgirish nxge_status_t 79144961713Sgirish nxge_fflp_set_hash2(p_nxge_t nxgep, uint16_t h2) 79244961713Sgirish { 79344961713Sgirish npi_status_t rs = NPI_SUCCESS; 79444961713Sgirish npi_handle_t handle; 795a3c5bd6dSspeer p_nxge_class_pt_cfg_t p_class_cfgp; 79644961713Sgirish 79744961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, " ==> nxge_fflp_init_h2")); 79844961713Sgirish p_class_cfgp = (p_nxge_class_pt_cfg_t)&nxgep->class_config; 79944961713Sgirish p_class_cfgp->init_h2 = h2; 80044961713Sgirish 80144961713Sgirish handle = nxgep->npi_reg_handle; 80244961713Sgirish rs = npi_fflp_cfg_hash_h2poly(handle, h2); 80344961713Sgirish if (rs & NPI_FFLP_ERROR) { 804a3c5bd6dSspeer NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 805*52ccf843Smisaki " nxge_fflp_init_h2 %x failed ", h2)); 80644961713Sgirish return (NXGE_ERROR | rs); 80744961713Sgirish } 80844961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, " <== nxge_fflp_init_h2")); 80944961713Sgirish return (NXGE_OK); 81044961713Sgirish } 81144961713Sgirish 81244961713Sgirish nxge_status_t 81344961713Sgirish nxge_classify_init_sw(p_nxge_t nxgep) 81444961713Sgirish { 81544961713Sgirish int alloc_size; 81644961713Sgirish nxge_classify_t *classify_ptr; 81744961713Sgirish 81844961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "==> nxge_classify_init_sw")); 81944961713Sgirish classify_ptr = &nxgep->classifier; 82044961713Sgirish 82144961713Sgirish if (classify_ptr->state & NXGE_FFLP_SW_INIT) { 82244961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 823*52ccf843Smisaki "nxge_classify_init_sw already init")); 82444961713Sgirish return (NXGE_OK); 82544961713Sgirish } 826a3c5bd6dSspeer /* Init SW structures */ 82744961713Sgirish classify_ptr->tcam_size = TCAM_NIU_TCAM_MAX_ENTRY; 828a3c5bd6dSspeer 829a3c5bd6dSspeer /* init data structures, based on HW type */ 8302e59129aSraghus if (NXGE_IS_VALID_NEPTUNE_TYPE(nxgep)) { 83144961713Sgirish classify_ptr->tcam_size = TCAM_NXGE_TCAM_MAX_ENTRY; 832a3c5bd6dSspeer /* 833a3c5bd6dSspeer * check if fcram based classification is required and init the 834a3c5bd6dSspeer * flow storage 835a3c5bd6dSspeer */ 83644961713Sgirish } 83744961713Sgirish alloc_size = sizeof (tcam_flow_spec_t) * classify_ptr->tcam_size; 83844961713Sgirish classify_ptr->tcam_entries = KMEM_ZALLOC(alloc_size, NULL); 83944961713Sgirish 840a3c5bd6dSspeer /* Init defaults */ 841a3c5bd6dSspeer /* 842a3c5bd6dSspeer * add hacks required for HW shortcomings for example, code to handle 843a3c5bd6dSspeer * fragmented packets 844a3c5bd6dSspeer */ 84544961713Sgirish nxge_init_h1_table(); 84644961713Sgirish nxge_crc_ccitt_init(); 84744961713Sgirish nxgep->classifier.tcam_location = nxgep->function_num; 84844961713Sgirish nxgep->classifier.fragment_bug = 1; 84944961713Sgirish classify_ptr->state |= NXGE_FFLP_SW_INIT; 85044961713Sgirish 85144961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "<== nxge_classify_init_sw")); 85244961713Sgirish return (NXGE_OK); 85344961713Sgirish } 85444961713Sgirish 85544961713Sgirish nxge_status_t 85644961713Sgirish nxge_classify_exit_sw(p_nxge_t nxgep) 85744961713Sgirish { 85844961713Sgirish int alloc_size; 85944961713Sgirish nxge_classify_t *classify_ptr; 86044961713Sgirish int fsize; 861a3c5bd6dSspeer 86244961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "==> nxge_classify_exit_sw")); 86344961713Sgirish classify_ptr = &nxgep->classifier; 86444961713Sgirish 86544961713Sgirish fsize = sizeof (tcam_flow_spec_t); 86644961713Sgirish if (classify_ptr->tcam_entries) { 867a3c5bd6dSspeer alloc_size = fsize * classify_ptr->tcam_size; 868a3c5bd6dSspeer KMEM_FREE((void *) classify_ptr->tcam_entries, alloc_size); 86944961713Sgirish } 87044961713Sgirish nxgep->classifier.state = NULL; 87144961713Sgirish 87244961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "<== nxge_classify_exit_sw")); 87344961713Sgirish return (NXGE_OK); 87444961713Sgirish } 87544961713Sgirish 87644961713Sgirish /* 87744961713Sgirish * Figures out the location where the TCAM entry is 87844961713Sgirish * to be inserted. 87944961713Sgirish * 88044961713Sgirish * The current implementation is just a place holder and it 88144961713Sgirish * returns the next tcam location. 88244961713Sgirish * The real location determining algorithm would consider 88344961713Sgirish * the priority, partition etc ... before deciding which 88444961713Sgirish * location to insert. 88544961713Sgirish * 88644961713Sgirish */ 88744961713Sgirish 8880a8e077aSspeer /* ARGSUSED */ 88944961713Sgirish static tcam_location_t 89044961713Sgirish nxge_get_tcam_location(p_nxge_t nxgep, uint8_t class) 89144961713Sgirish { 89244961713Sgirish tcam_location_t location; 893a3c5bd6dSspeer 89444961713Sgirish location = nxgep->classifier.tcam_location; 89544961713Sgirish nxgep->classifier.tcam_location = (location + nxgep->nports) % 896*52ccf843Smisaki nxgep->classifier.tcam_size; 89744961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 898*52ccf843Smisaki "nxge_get_tcam_location: location %d next %d \n", 899*52ccf843Smisaki location, nxgep->classifier.tcam_location)); 90044961713Sgirish return (location); 90144961713Sgirish } 90244961713Sgirish 90344961713Sgirish /* 90444961713Sgirish * Figures out the RDC Group for the entry 90544961713Sgirish * 90644961713Sgirish * The current implementation is just a place holder and it 90744961713Sgirish * returns 0. 90844961713Sgirish * The real location determining algorithm would consider 90944961713Sgirish * the partition etc ... before deciding w 91044961713Sgirish * 91144961713Sgirish */ 912a3c5bd6dSspeer 9130a8e077aSspeer /* ARGSUSED */ 91444961713Sgirish static uint8_t 91544961713Sgirish nxge_get_rdc_group(p_nxge_t nxgep, uint8_t class, intptr_t cookie) 91644961713Sgirish { 91744961713Sgirish int use_port_rdc_grp = 0; 91844961713Sgirish uint8_t rdc_grp = 0; 919a3c5bd6dSspeer p_nxge_dma_pt_cfg_t p_dma_cfgp; 920a3c5bd6dSspeer p_nxge_hw_pt_cfg_t p_cfgp; 921a3c5bd6dSspeer p_nxge_rdc_grp_t rdc_grp_p; 922a3c5bd6dSspeer 92344961713Sgirish p_dma_cfgp = (p_nxge_dma_pt_cfg_t)&nxgep->pt_config; 92444961713Sgirish p_cfgp = (p_nxge_hw_pt_cfg_t)&p_dma_cfgp->hw_config; 92544961713Sgirish rdc_grp_p = &p_dma_cfgp->rdc_grps[use_port_rdc_grp]; 926678453a8Sspeer rdc_grp = p_cfgp->def_mac_rxdma_grpid; 927a3c5bd6dSspeer 92844961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 929*52ccf843Smisaki "nxge_get_rdc_group: grp 0x%x real_grp %x grpp $%p\n", 930*52ccf843Smisaki cookie, rdc_grp, rdc_grp_p)); 93144961713Sgirish return (rdc_grp); 93244961713Sgirish } 93344961713Sgirish 93444961713Sgirish /* ARGSUSED */ 93544961713Sgirish static uint8_t 93644961713Sgirish nxge_get_rdc_offset(p_nxge_t nxgep, uint8_t class, intptr_t cookie) 93744961713Sgirish { 93844961713Sgirish return ((uint8_t)cookie); 93944961713Sgirish } 94044961713Sgirish 9410a8e077aSspeer /* ARGSUSED */ 94244961713Sgirish static void 94344961713Sgirish nxge_fill_tcam_entry_udp(p_nxge_t nxgep, flow_spec_t *flow_spec, 944a3c5bd6dSspeer tcam_entry_t *tcam_ptr) 94544961713Sgirish { 94644961713Sgirish udpip4_spec_t *fspec_key; 94744961713Sgirish udpip4_spec_t *fspec_mask; 94844961713Sgirish 94944961713Sgirish fspec_key = (udpip4_spec_t *)&flow_spec->uh.udpip4spec; 95044961713Sgirish fspec_mask = (udpip4_spec_t *)&flow_spec->um.udpip4spec; 95144961713Sgirish TCAM_IPV4_ADDR(tcam_ptr->ip4_dest_key, fspec_key->ip4dst); 95244961713Sgirish TCAM_IPV4_ADDR(tcam_ptr->ip4_dest_mask, fspec_mask->ip4dst); 95344961713Sgirish TCAM_IPV4_ADDR(tcam_ptr->ip4_src_key, fspec_key->ip4src); 95444961713Sgirish TCAM_IPV4_ADDR(tcam_ptr->ip4_src_mask, fspec_mask->ip4src); 95544961713Sgirish TCAM_IP_PORTS(tcam_ptr->ip4_port_key, 956*52ccf843Smisaki fspec_key->pdst, fspec_key->psrc); 95744961713Sgirish TCAM_IP_PORTS(tcam_ptr->ip4_port_mask, 958*52ccf843Smisaki fspec_mask->pdst, fspec_mask->psrc); 95944961713Sgirish TCAM_IP_CLASS(tcam_ptr->ip4_class_key, 960*52ccf843Smisaki tcam_ptr->ip4_class_mask, 961*52ccf843Smisaki TCAM_CLASS_UDP_IPV4); 96244961713Sgirish TCAM_IP_PROTO(tcam_ptr->ip4_proto_key, 963*52ccf843Smisaki tcam_ptr->ip4_proto_mask, 964*52ccf843Smisaki IPPROTO_UDP); 96544961713Sgirish } 96644961713Sgirish 96744961713Sgirish static void 96844961713Sgirish nxge_fill_tcam_entry_udp_ipv6(p_nxge_t nxgep, flow_spec_t *flow_spec, 969a3c5bd6dSspeer tcam_entry_t *tcam_ptr) 97044961713Sgirish { 97144961713Sgirish udpip6_spec_t *fspec_key; 97244961713Sgirish udpip6_spec_t *fspec_mask; 973a3c5bd6dSspeer p_nxge_class_pt_cfg_t p_class_cfgp; 97444961713Sgirish 97544961713Sgirish fspec_key = (udpip6_spec_t *)&flow_spec->uh.udpip6spec; 97644961713Sgirish fspec_mask = (udpip6_spec_t *)&flow_spec->um.udpip6spec; 97744961713Sgirish p_class_cfgp = (p_nxge_class_pt_cfg_t)&nxgep->class_config; 97844961713Sgirish if (p_class_cfgp->class_cfg[TCAM_CLASS_UDP_IPV6] & 979*52ccf843Smisaki NXGE_CLASS_TCAM_USE_SRC_ADDR) { 98044961713Sgirish TCAM_IPV6_ADDR(tcam_ptr->ip6_ip_addr_key, fspec_key->ip6src); 98144961713Sgirish TCAM_IPV6_ADDR(tcam_ptr->ip6_ip_addr_mask, fspec_mask->ip6src); 98244961713Sgirish } else { 98344961713Sgirish TCAM_IPV6_ADDR(tcam_ptr->ip6_ip_addr_key, fspec_key->ip6dst); 98444961713Sgirish TCAM_IPV6_ADDR(tcam_ptr->ip6_ip_addr_mask, fspec_mask->ip6dst); 98544961713Sgirish } 98644961713Sgirish 98744961713Sgirish TCAM_IP_CLASS(tcam_ptr->ip6_class_key, 988*52ccf843Smisaki tcam_ptr->ip6_class_mask, TCAM_CLASS_UDP_IPV6); 98944961713Sgirish TCAM_IP_PROTO(tcam_ptr->ip6_nxt_hdr_key, 990*52ccf843Smisaki tcam_ptr->ip6_nxt_hdr_mask, IPPROTO_UDP); 99144961713Sgirish TCAM_IP_PORTS(tcam_ptr->ip6_port_key, 992*52ccf843Smisaki fspec_key->pdst, fspec_key->psrc); 99344961713Sgirish TCAM_IP_PORTS(tcam_ptr->ip6_port_mask, 994*52ccf843Smisaki fspec_mask->pdst, fspec_mask->psrc); 99544961713Sgirish } 99644961713Sgirish 9970a8e077aSspeer /* ARGSUSED */ 99844961713Sgirish static void 99944961713Sgirish nxge_fill_tcam_entry_tcp(p_nxge_t nxgep, flow_spec_t *flow_spec, 1000a3c5bd6dSspeer tcam_entry_t *tcam_ptr) 100144961713Sgirish { 100244961713Sgirish tcpip4_spec_t *fspec_key; 100344961713Sgirish tcpip4_spec_t *fspec_mask; 100444961713Sgirish 100544961713Sgirish fspec_key = (tcpip4_spec_t *)&flow_spec->uh.tcpip4spec; 100644961713Sgirish fspec_mask = (tcpip4_spec_t *)&flow_spec->um.tcpip4spec; 100744961713Sgirish 100844961713Sgirish TCAM_IPV4_ADDR(tcam_ptr->ip4_dest_key, fspec_key->ip4dst); 100944961713Sgirish TCAM_IPV4_ADDR(tcam_ptr->ip4_dest_mask, fspec_mask->ip4dst); 101044961713Sgirish TCAM_IPV4_ADDR(tcam_ptr->ip4_src_key, fspec_key->ip4src); 101144961713Sgirish TCAM_IPV4_ADDR(tcam_ptr->ip4_src_mask, fspec_mask->ip4src); 101244961713Sgirish TCAM_IP_PORTS(tcam_ptr->ip4_port_key, 1013*52ccf843Smisaki fspec_key->pdst, fspec_key->psrc); 101444961713Sgirish TCAM_IP_PORTS(tcam_ptr->ip4_port_mask, 1015*52ccf843Smisaki fspec_mask->pdst, fspec_mask->psrc); 101644961713Sgirish TCAM_IP_CLASS(tcam_ptr->ip4_class_key, 1017*52ccf843Smisaki tcam_ptr->ip4_class_mask, TCAM_CLASS_TCP_IPV4); 101844961713Sgirish TCAM_IP_PROTO(tcam_ptr->ip4_proto_key, 1019*52ccf843Smisaki tcam_ptr->ip4_proto_mask, IPPROTO_TCP); 102044961713Sgirish } 102144961713Sgirish 10220a8e077aSspeer /* ARGSUSED */ 102344961713Sgirish static void 102444961713Sgirish nxge_fill_tcam_entry_sctp(p_nxge_t nxgep, flow_spec_t *flow_spec, 1025a3c5bd6dSspeer tcam_entry_t *tcam_ptr) 102644961713Sgirish { 102744961713Sgirish tcpip4_spec_t *fspec_key; 102844961713Sgirish tcpip4_spec_t *fspec_mask; 102944961713Sgirish 103044961713Sgirish fspec_key = (tcpip4_spec_t *)&flow_spec->uh.tcpip4spec; 103144961713Sgirish fspec_mask = (tcpip4_spec_t *)&flow_spec->um.tcpip4spec; 103244961713Sgirish 103344961713Sgirish TCAM_IPV4_ADDR(tcam_ptr->ip4_dest_key, fspec_key->ip4dst); 103444961713Sgirish TCAM_IPV4_ADDR(tcam_ptr->ip4_dest_mask, fspec_mask->ip4dst); 103544961713Sgirish TCAM_IPV4_ADDR(tcam_ptr->ip4_src_key, fspec_key->ip4src); 103644961713Sgirish TCAM_IPV4_ADDR(tcam_ptr->ip4_src_mask, fspec_mask->ip4src); 103744961713Sgirish TCAM_IP_CLASS(tcam_ptr->ip4_class_key, 1038*52ccf843Smisaki tcam_ptr->ip4_class_mask, TCAM_CLASS_SCTP_IPV4); 103944961713Sgirish TCAM_IP_PROTO(tcam_ptr->ip4_proto_key, 1040*52ccf843Smisaki tcam_ptr->ip4_proto_mask, IPPROTO_SCTP); 104144961713Sgirish TCAM_IP_PORTS(tcam_ptr->ip4_port_key, 1042*52ccf843Smisaki fspec_key->pdst, fspec_key->psrc); 104344961713Sgirish TCAM_IP_PORTS(tcam_ptr->ip4_port_mask, 1044*52ccf843Smisaki fspec_mask->pdst, fspec_mask->psrc); 104544961713Sgirish } 104644961713Sgirish 104744961713Sgirish static void 104844961713Sgirish nxge_fill_tcam_entry_tcp_ipv6(p_nxge_t nxgep, flow_spec_t *flow_spec, 1049a3c5bd6dSspeer tcam_entry_t *tcam_ptr) 105044961713Sgirish { 105144961713Sgirish tcpip6_spec_t *fspec_key; 105244961713Sgirish tcpip6_spec_t *fspec_mask; 1053a3c5bd6dSspeer p_nxge_class_pt_cfg_t p_class_cfgp; 1054a3c5bd6dSspeer 105544961713Sgirish fspec_key = (tcpip6_spec_t *)&flow_spec->uh.tcpip6spec; 105644961713Sgirish fspec_mask = (tcpip6_spec_t *)&flow_spec->um.tcpip6spec; 105744961713Sgirish 105844961713Sgirish p_class_cfgp = (p_nxge_class_pt_cfg_t)&nxgep->class_config; 105944961713Sgirish if (p_class_cfgp->class_cfg[TCAM_CLASS_UDP_IPV6] & 1060*52ccf843Smisaki NXGE_CLASS_TCAM_USE_SRC_ADDR) { 106144961713Sgirish TCAM_IPV6_ADDR(tcam_ptr->ip6_ip_addr_key, fspec_key->ip6src); 106244961713Sgirish TCAM_IPV6_ADDR(tcam_ptr->ip6_ip_addr_mask, fspec_mask->ip6src); 106344961713Sgirish } else { 106444961713Sgirish TCAM_IPV6_ADDR(tcam_ptr->ip6_ip_addr_key, fspec_key->ip6dst); 106544961713Sgirish TCAM_IPV6_ADDR(tcam_ptr->ip6_ip_addr_mask, fspec_mask->ip6dst); 106644961713Sgirish } 106744961713Sgirish 106844961713Sgirish TCAM_IP_CLASS(tcam_ptr->ip6_class_key, 1069*52ccf843Smisaki tcam_ptr->ip6_class_mask, TCAM_CLASS_TCP_IPV6); 107044961713Sgirish TCAM_IP_PROTO(tcam_ptr->ip6_nxt_hdr_key, 1071*52ccf843Smisaki tcam_ptr->ip6_nxt_hdr_mask, IPPROTO_TCP); 107244961713Sgirish TCAM_IP_PORTS(tcam_ptr->ip6_port_key, 1073*52ccf843Smisaki fspec_key->pdst, fspec_key->psrc); 107444961713Sgirish TCAM_IP_PORTS(tcam_ptr->ip6_port_mask, 1075*52ccf843Smisaki fspec_mask->pdst, fspec_mask->psrc); 107644961713Sgirish } 107744961713Sgirish 107844961713Sgirish static void 107944961713Sgirish nxge_fill_tcam_entry_sctp_ipv6(p_nxge_t nxgep, flow_spec_t *flow_spec, 1080a3c5bd6dSspeer tcam_entry_t *tcam_ptr) 108144961713Sgirish { 108244961713Sgirish tcpip6_spec_t *fspec_key; 108344961713Sgirish tcpip6_spec_t *fspec_mask; 1084a3c5bd6dSspeer p_nxge_class_pt_cfg_t p_class_cfgp; 108544961713Sgirish 108644961713Sgirish fspec_key = (tcpip6_spec_t *)&flow_spec->uh.tcpip6spec; 108744961713Sgirish fspec_mask = (tcpip6_spec_t *)&flow_spec->um.tcpip6spec; 108844961713Sgirish p_class_cfgp = (p_nxge_class_pt_cfg_t)&nxgep->class_config; 108944961713Sgirish 109044961713Sgirish if (p_class_cfgp->class_cfg[TCAM_CLASS_UDP_IPV6] & 1091*52ccf843Smisaki NXGE_CLASS_TCAM_USE_SRC_ADDR) { 109244961713Sgirish TCAM_IPV6_ADDR(tcam_ptr->ip6_ip_addr_key, fspec_key->ip6src); 109344961713Sgirish TCAM_IPV6_ADDR(tcam_ptr->ip6_ip_addr_mask, fspec_mask->ip6src); 109444961713Sgirish } else { 109544961713Sgirish TCAM_IPV6_ADDR(tcam_ptr->ip6_ip_addr_key, fspec_key->ip6dst); 109644961713Sgirish TCAM_IPV6_ADDR(tcam_ptr->ip6_ip_addr_mask, fspec_mask->ip6dst); 109744961713Sgirish } 109844961713Sgirish 109944961713Sgirish TCAM_IP_CLASS(tcam_ptr->ip6_class_key, 1100*52ccf843Smisaki tcam_ptr->ip6_class_mask, TCAM_CLASS_SCTP_IPV6); 110144961713Sgirish TCAM_IP_PROTO(tcam_ptr->ip6_nxt_hdr_key, 1102*52ccf843Smisaki tcam_ptr->ip6_nxt_hdr_mask, IPPROTO_SCTP); 110344961713Sgirish TCAM_IP_PORTS(tcam_ptr->ip6_port_key, 1104*52ccf843Smisaki fspec_key->pdst, fspec_key->psrc); 110544961713Sgirish TCAM_IP_PORTS(tcam_ptr->ip6_port_mask, 1106*52ccf843Smisaki fspec_mask->pdst, fspec_mask->psrc); 110744961713Sgirish } 110844961713Sgirish 110944961713Sgirish nxge_status_t 111044961713Sgirish nxge_flow_get_hash(p_nxge_t nxgep, flow_resource_t *flow_res, 1111a3c5bd6dSspeer uint32_t *H1, uint16_t *H2) 111244961713Sgirish { 111344961713Sgirish flow_spec_t *flow_spec; 111444961713Sgirish uint32_t class_cfg; 111544961713Sgirish flow_template_t ft; 1116a3c5bd6dSspeer p_nxge_class_pt_cfg_t p_class_cfgp; 111744961713Sgirish 111844961713Sgirish int ft_size = sizeof (flow_template_t); 1119a3c5bd6dSspeer 112044961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "==> nxge_flow_get_hash")); 112144961713Sgirish 112244961713Sgirish flow_spec = (flow_spec_t *)&flow_res->flow_spec; 112344961713Sgirish bzero((char *)&ft, ft_size); 112444961713Sgirish p_class_cfgp = (p_nxge_class_pt_cfg_t)&nxgep->class_config; 1125a3c5bd6dSspeer 112644961713Sgirish switch (flow_spec->flow_type) { 1127a3c5bd6dSspeer case FSPEC_TCPIP4: 1128a3c5bd6dSspeer class_cfg = p_class_cfgp->class_cfg[TCAM_CLASS_TCP_IPV4]; 1129a3c5bd6dSspeer if (class_cfg & NXGE_CLASS_FLOW_USE_PROTO) 1130a3c5bd6dSspeer ft.ip_proto = IPPROTO_TCP; 1131a3c5bd6dSspeer if (class_cfg & NXGE_CLASS_FLOW_USE_IPSRC) 1132a3c5bd6dSspeer ft.ip4_saddr = flow_res->flow_spec.uh.tcpip4spec.ip4src; 1133a3c5bd6dSspeer if (class_cfg & NXGE_CLASS_FLOW_USE_IPDST) 1134a3c5bd6dSspeer ft.ip4_daddr = flow_res->flow_spec.uh.tcpip4spec.ip4dst; 1135a3c5bd6dSspeer if (class_cfg & NXGE_CLASS_FLOW_USE_SRC_PORT) 1136a3c5bd6dSspeer ft.ip_src_port = flow_res->flow_spec.uh.tcpip4spec.psrc; 1137a3c5bd6dSspeer if (class_cfg & NXGE_CLASS_FLOW_USE_DST_PORT) 1138a3c5bd6dSspeer ft.ip_dst_port = flow_res->flow_spec.uh.tcpip4spec.pdst; 1139a3c5bd6dSspeer break; 1140a3c5bd6dSspeer 1141a3c5bd6dSspeer case FSPEC_UDPIP4: 1142a3c5bd6dSspeer class_cfg = p_class_cfgp->class_cfg[TCAM_CLASS_UDP_IPV4]; 1143a3c5bd6dSspeer if (class_cfg & NXGE_CLASS_FLOW_USE_PROTO) 1144a3c5bd6dSspeer ft.ip_proto = IPPROTO_UDP; 1145a3c5bd6dSspeer if (class_cfg & NXGE_CLASS_FLOW_USE_IPSRC) 1146a3c5bd6dSspeer ft.ip4_saddr = flow_res->flow_spec.uh.udpip4spec.ip4src; 1147a3c5bd6dSspeer if (class_cfg & NXGE_CLASS_FLOW_USE_IPDST) 1148a3c5bd6dSspeer ft.ip4_daddr = flow_res->flow_spec.uh.udpip4spec.ip4dst; 1149a3c5bd6dSspeer if (class_cfg & NXGE_CLASS_FLOW_USE_SRC_PORT) 1150a3c5bd6dSspeer ft.ip_src_port = flow_res->flow_spec.uh.udpip4spec.psrc; 1151a3c5bd6dSspeer if (class_cfg & NXGE_CLASS_FLOW_USE_DST_PORT) 1152a3c5bd6dSspeer ft.ip_dst_port = flow_res->flow_spec.uh.udpip4spec.pdst; 1153a3c5bd6dSspeer break; 1154a3c5bd6dSspeer 1155a3c5bd6dSspeer default: 1156a3c5bd6dSspeer return (NXGE_ERROR); 115744961713Sgirish } 115844961713Sgirish 115944961713Sgirish *H1 = nxge_compute_h1(p_class_cfgp->init_h1, 1160*52ccf843Smisaki (uint32_t *)&ft, ft_size) & 0xfffff; 116144961713Sgirish *H2 = nxge_compute_h2(p_class_cfgp->init_h2, 1162*52ccf843Smisaki (uint8_t *)&ft, ft_size); 116344961713Sgirish 116444961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "<== nxge_flow_get_hash")); 116544961713Sgirish return (NXGE_OK); 116644961713Sgirish } 116744961713Sgirish 116844961713Sgirish nxge_status_t 116944961713Sgirish nxge_add_fcram_entry(p_nxge_t nxgep, flow_resource_t *flow_res) 117044961713Sgirish { 117144961713Sgirish uint32_t H1; 117244961713Sgirish uint16_t H2; 117344961713Sgirish nxge_status_t status = NXGE_OK; 117444961713Sgirish 117544961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "==> nxge_add_fcram_entry")); 117644961713Sgirish status = nxge_flow_get_hash(nxgep, flow_res, &H1, &H2); 117744961713Sgirish if (status != NXGE_OK) { 117844961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1179*52ccf843Smisaki " nxge_add_fcram_entry failed ")); 118044961713Sgirish return (status); 118144961713Sgirish } 118244961713Sgirish 118344961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "<== nxge_add_fcram_entry")); 118444961713Sgirish return (NXGE_OK); 118544961713Sgirish } 118644961713Sgirish 118744961713Sgirish /* 118844961713Sgirish * Already decided this flow goes into the tcam 118944961713Sgirish */ 119044961713Sgirish 119144961713Sgirish nxge_status_t 119244961713Sgirish nxge_add_tcam_entry(p_nxge_t nxgep, flow_resource_t *flow_res) 119344961713Sgirish { 119444961713Sgirish npi_handle_t handle; 119544961713Sgirish intptr_t channel_cookie; 119644961713Sgirish intptr_t flow_cookie; 119744961713Sgirish flow_spec_t *flow_spec; 119844961713Sgirish npi_status_t rs = NPI_SUCCESS; 119944961713Sgirish tcam_entry_t tcam_ptr; 120044961713Sgirish tcam_location_t location = 0; 120144961713Sgirish uint8_t offset, rdc_grp; 1202a3c5bd6dSspeer p_nxge_hw_list_t hw_p; 120344961713Sgirish 120444961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "==> nxge_add_tcam_entry")); 120544961713Sgirish handle = nxgep->npi_reg_handle; 120644961713Sgirish 1207a3c5bd6dSspeer bzero((void *)&tcam_ptr, sizeof (tcam_entry_t)); 120844961713Sgirish flow_spec = (flow_spec_t *)&flow_res->flow_spec; 120944961713Sgirish flow_cookie = flow_res->flow_cookie; 121044961713Sgirish channel_cookie = flow_res->channel_cookie; 121144961713Sgirish 121244961713Sgirish switch (flow_spec->flow_type) { 1213a3c5bd6dSspeer case FSPEC_TCPIP4: 1214a3c5bd6dSspeer nxge_fill_tcam_entry_tcp(nxgep, flow_spec, &tcam_ptr); 1215a3c5bd6dSspeer location = nxge_get_tcam_location(nxgep, 1216*52ccf843Smisaki TCAM_CLASS_TCP_IPV4); 1217a3c5bd6dSspeer rdc_grp = nxge_get_rdc_group(nxgep, TCAM_CLASS_TCP_IPV4, 1218*52ccf843Smisaki flow_cookie); 1219a3c5bd6dSspeer offset = nxge_get_rdc_offset(nxgep, TCAM_CLASS_TCP_IPV4, 1220*52ccf843Smisaki channel_cookie); 1221a3c5bd6dSspeer break; 1222a3c5bd6dSspeer 1223a3c5bd6dSspeer case FSPEC_UDPIP4: 1224a3c5bd6dSspeer nxge_fill_tcam_entry_udp(nxgep, flow_spec, &tcam_ptr); 1225a3c5bd6dSspeer location = nxge_get_tcam_location(nxgep, 1226*52ccf843Smisaki TCAM_CLASS_UDP_IPV4); 1227a3c5bd6dSspeer rdc_grp = nxge_get_rdc_group(nxgep, 1228*52ccf843Smisaki TCAM_CLASS_UDP_IPV4, 1229*52ccf843Smisaki flow_cookie); 1230a3c5bd6dSspeer offset = nxge_get_rdc_offset(nxgep, 1231*52ccf843Smisaki TCAM_CLASS_UDP_IPV4, 1232*52ccf843Smisaki channel_cookie); 1233a3c5bd6dSspeer break; 1234a3c5bd6dSspeer 1235a3c5bd6dSspeer case FSPEC_TCPIP6: 1236a3c5bd6dSspeer nxge_fill_tcam_entry_tcp_ipv6(nxgep, 1237*52ccf843Smisaki flow_spec, &tcam_ptr); 1238a3c5bd6dSspeer location = nxge_get_tcam_location(nxgep, 1239*52ccf843Smisaki TCAM_CLASS_TCP_IPV6); 1240a3c5bd6dSspeer rdc_grp = nxge_get_rdc_group(nxgep, TCAM_CLASS_TCP_IPV6, 1241*52ccf843Smisaki flow_cookie); 1242a3c5bd6dSspeer offset = nxge_get_rdc_offset(nxgep, TCAM_CLASS_TCP_IPV6, 1243*52ccf843Smisaki channel_cookie); 1244a3c5bd6dSspeer break; 1245a3c5bd6dSspeer 1246a3c5bd6dSspeer case FSPEC_UDPIP6: 1247a3c5bd6dSspeer nxge_fill_tcam_entry_udp_ipv6(nxgep, 1248*52ccf843Smisaki flow_spec, &tcam_ptr); 1249a3c5bd6dSspeer location = nxge_get_tcam_location(nxgep, 1250*52ccf843Smisaki TCAM_CLASS_UDP_IPV6); 1251a3c5bd6dSspeer rdc_grp = nxge_get_rdc_group(nxgep, 1252*52ccf843Smisaki TCAM_CLASS_UDP_IPV6, 1253*52ccf843Smisaki channel_cookie); 1254a3c5bd6dSspeer offset = nxge_get_rdc_offset(nxgep, 1255*52ccf843Smisaki TCAM_CLASS_UDP_IPV6, 1256*52ccf843Smisaki flow_cookie); 1257a3c5bd6dSspeer break; 1258a3c5bd6dSspeer 1259a3c5bd6dSspeer case FSPEC_SCTPIP4: 1260a3c5bd6dSspeer nxge_fill_tcam_entry_sctp(nxgep, flow_spec, &tcam_ptr); 1261a3c5bd6dSspeer location = nxge_get_tcam_location(nxgep, 1262*52ccf843Smisaki TCAM_CLASS_SCTP_IPV4); 1263a3c5bd6dSspeer rdc_grp = nxge_get_rdc_group(nxgep, 1264*52ccf843Smisaki TCAM_CLASS_SCTP_IPV4, 1265*52ccf843Smisaki channel_cookie); 1266a3c5bd6dSspeer offset = nxge_get_rdc_offset(nxgep, 1267*52ccf843Smisaki TCAM_CLASS_SCTP_IPV4, 1268*52ccf843Smisaki flow_cookie); 1269a3c5bd6dSspeer break; 1270a3c5bd6dSspeer 1271a3c5bd6dSspeer case FSPEC_SCTPIP6: 1272a3c5bd6dSspeer nxge_fill_tcam_entry_sctp_ipv6(nxgep, 1273*52ccf843Smisaki flow_spec, &tcam_ptr); 1274a3c5bd6dSspeer location = nxge_get_tcam_location(nxgep, 1275*52ccf843Smisaki TCAM_CLASS_SCTP_IPV4); 1276a3c5bd6dSspeer rdc_grp = nxge_get_rdc_group(nxgep, 1277*52ccf843Smisaki TCAM_CLASS_SCTP_IPV6, 1278*52ccf843Smisaki channel_cookie); 1279a3c5bd6dSspeer offset = nxge_get_rdc_offset(nxgep, 1280*52ccf843Smisaki TCAM_CLASS_SCTP_IPV6, 1281*52ccf843Smisaki flow_cookie); 1282a3c5bd6dSspeer break; 1283a3c5bd6dSspeer 1284a3c5bd6dSspeer default: 1285a3c5bd6dSspeer return (NXGE_OK); 128644961713Sgirish } 128744961713Sgirish 128844961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1289*52ccf843Smisaki " nxge_add_tcam_entry write" 1290*52ccf843Smisaki " for location %d offset %d", location, offset)); 129144961713Sgirish 129244961713Sgirish if ((hw_p = nxgep->nxge_hw_p) == NULL) { 129344961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1294*52ccf843Smisaki " nxge_add_tcam_entry: common hardware not set", 1295*52ccf843Smisaki nxgep->niu_type)); 129644961713Sgirish return (NXGE_ERROR); 129744961713Sgirish } 1298a3c5bd6dSspeer 129944961713Sgirish MUTEX_ENTER(&hw_p->nxge_tcam_lock); 1300a3c5bd6dSspeer rs = npi_fflp_tcam_entry_write(handle, location, &tcam_ptr); 130144961713Sgirish 130244961713Sgirish if (rs & NPI_FFLP_ERROR) { 130344961713Sgirish MUTEX_EXIT(&hw_p->nxge_tcam_lock); 130444961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1305*52ccf843Smisaki " nxge_add_tcam_entry write" 1306*52ccf843Smisaki " failed for location %d", location)); 130744961713Sgirish return (NXGE_ERROR | rs); 130844961713Sgirish } 1309a3c5bd6dSspeer 131044961713Sgirish tcam_ptr.match_action.value = 0; 131144961713Sgirish tcam_ptr.match_action.bits.ldw.rdctbl = rdc_grp; 131244961713Sgirish tcam_ptr.match_action.bits.ldw.offset = offset; 131344961713Sgirish tcam_ptr.match_action.bits.ldw.tres = 1314*52ccf843Smisaki TRES_TERM_OVRD_L2RDC; 131544961713Sgirish if (channel_cookie == -1) 131644961713Sgirish tcam_ptr.match_action.bits.ldw.disc = 1; 131744961713Sgirish rs = npi_fflp_tcam_asc_ram_entry_write(handle, 1318*52ccf843Smisaki location, tcam_ptr.match_action.value); 131944961713Sgirish if (rs & NPI_FFLP_ERROR) { 132044961713Sgirish MUTEX_EXIT(&hw_p->nxge_tcam_lock); 132144961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1322*52ccf843Smisaki " nxge_add_tcam_entry write" 1323*52ccf843Smisaki " failed for ASC RAM location %d", location)); 132444961713Sgirish return (NXGE_ERROR | rs); 132544961713Sgirish } 1326a3c5bd6dSspeer bcopy((void *) &tcam_ptr, 1327*52ccf843Smisaki (void *) &nxgep->classifier.tcam_entries[location].tce, 1328*52ccf843Smisaki sizeof (tcam_entry_t)); 132944961713Sgirish 133044961713Sgirish MUTEX_EXIT(&hw_p->nxge_tcam_lock); 133144961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "<== nxge_add_tcam_entry")); 133244961713Sgirish return (NXGE_OK); 133344961713Sgirish } 133444961713Sgirish 133514ea4bb7Ssd static nxge_status_t 133614ea4bb7Ssd nxge_tcam_handle_ip_fragment(p_nxge_t nxgep) 133744961713Sgirish { 133844961713Sgirish tcam_entry_t tcam_ptr; 133944961713Sgirish tcam_location_t location; 134044961713Sgirish uint8_t class; 134114ea4bb7Ssd uint32_t class_config; 134244961713Sgirish npi_handle_t handle; 134344961713Sgirish npi_status_t rs = NPI_SUCCESS; 1344a3c5bd6dSspeer p_nxge_hw_list_t hw_p; 134514ea4bb7Ssd nxge_status_t status = NXGE_OK; 134644961713Sgirish 134744961713Sgirish handle = nxgep->npi_reg_handle; 134844961713Sgirish class = 0; 1349a3c5bd6dSspeer bzero((void *)&tcam_ptr, sizeof (tcam_entry_t)); 135044961713Sgirish tcam_ptr.ip4_noport_key = 1; 135144961713Sgirish tcam_ptr.ip4_noport_mask = 1; 135214ea4bb7Ssd location = nxgep->function_num; 135344961713Sgirish nxgep->classifier.fragment_bug_location = location; 135444961713Sgirish 135544961713Sgirish if ((hw_p = nxgep->nxge_hw_p) == NULL) { 135644961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1357*52ccf843Smisaki " nxge_tcam_handle_ip_fragment: common hardware not set", 1358*52ccf843Smisaki nxgep->niu_type)); 135914ea4bb7Ssd return (NXGE_ERROR); 136044961713Sgirish } 136144961713Sgirish MUTEX_ENTER(&hw_p->nxge_tcam_lock); 136244961713Sgirish rs = npi_fflp_tcam_entry_write(handle, 1363*52ccf843Smisaki location, &tcam_ptr); 136444961713Sgirish 136544961713Sgirish if (rs & NPI_FFLP_ERROR) { 136644961713Sgirish MUTEX_EXIT(&hw_p->nxge_tcam_lock); 136744961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1368*52ccf843Smisaki " nxge_tcam_handle_ip_fragment " 1369*52ccf843Smisaki " tcam_entry write" 1370*52ccf843Smisaki " failed for location %d", location)); 137114ea4bb7Ssd return (NXGE_ERROR); 137244961713Sgirish } 137344961713Sgirish tcam_ptr.match_action.bits.ldw.rdctbl = nxgep->class_config.mac_rdcgrp; 1374a3c5bd6dSspeer tcam_ptr.match_action.bits.ldw.offset = 0; /* use the default */ 137544961713Sgirish tcam_ptr.match_action.bits.ldw.tres = 1376*52ccf843Smisaki TRES_TERM_USE_OFFSET; 137744961713Sgirish rs = npi_fflp_tcam_asc_ram_entry_write(handle, 1378*52ccf843Smisaki location, tcam_ptr.match_action.value); 137944961713Sgirish 138044961713Sgirish if (rs & NPI_FFLP_ERROR) { 138144961713Sgirish MUTEX_EXIT(&hw_p->nxge_tcam_lock); 138244961713Sgirish NXGE_DEBUG_MSG((nxgep, 1383*52ccf843Smisaki FFLP_CTL, 1384*52ccf843Smisaki " nxge_tcam_handle_ip_fragment " 1385*52ccf843Smisaki " tcam_entry write" 1386*52ccf843Smisaki " failed for ASC RAM location %d", location)); 138714ea4bb7Ssd return (NXGE_ERROR); 138844961713Sgirish } 1389a3c5bd6dSspeer bcopy((void *) &tcam_ptr, 1390*52ccf843Smisaki (void *) &nxgep->classifier.tcam_entries[location].tce, 1391*52ccf843Smisaki sizeof (tcam_entry_t)); 139214ea4bb7Ssd for (class = TCAM_CLASS_TCP_IPV4; 1393*52ccf843Smisaki class <= TCAM_CLASS_SCTP_IPV6; class++) { 139414ea4bb7Ssd class_config = nxgep->class_config.class_cfg[class]; 139514ea4bb7Ssd class_config |= NXGE_CLASS_TCAM_LOOKUP; 139614ea4bb7Ssd status = nxge_fflp_ip_class_config(nxgep, class, class_config); 139714ea4bb7Ssd 139814ea4bb7Ssd if (status & NPI_FFLP_ERROR) { 139914ea4bb7Ssd MUTEX_EXIT(&hw_p->nxge_tcam_lock); 140014ea4bb7Ssd NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1401*52ccf843Smisaki "nxge_tcam_handle_ip_fragment " 1402*52ccf843Smisaki "nxge_fflp_ip_class_config failed " 1403*52ccf843Smisaki " class %d config %x ", class, class_config)); 140414ea4bb7Ssd return (NXGE_ERROR); 140514ea4bb7Ssd } 140614ea4bb7Ssd } 140714ea4bb7Ssd 140814ea4bb7Ssd rs = npi_fflp_cfg_tcam_enable(handle); 140914ea4bb7Ssd if (rs & NPI_FFLP_ERROR) { 141014ea4bb7Ssd MUTEX_EXIT(&hw_p->nxge_tcam_lock); 141114ea4bb7Ssd NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1412*52ccf843Smisaki "nxge_tcam_handle_ip_fragment " 1413*52ccf843Smisaki " nxge_fflp_config_tcam_enable failed")); 141414ea4bb7Ssd return (NXGE_ERROR); 141514ea4bb7Ssd } 141644961713Sgirish MUTEX_EXIT(&hw_p->nxge_tcam_lock); 141714ea4bb7Ssd return (NXGE_OK); 141844961713Sgirish } 141944961713Sgirish 142044961713Sgirish /* ARGSUSED */ 142144961713Sgirish static int 1422a3c5bd6dSspeer nxge_flow_need_hash_lookup(p_nxge_t nxgep, flow_resource_t *flow_res) 142344961713Sgirish { 142444961713Sgirish return (0); 142544961713Sgirish } 142644961713Sgirish 142744961713Sgirish nxge_status_t 142844961713Sgirish nxge_add_flow(p_nxge_t nxgep, flow_resource_t *flow_res) 142944961713Sgirish { 143044961713Sgirish 143144961713Sgirish int insert_hash = 0; 143244961713Sgirish nxge_status_t status = NXGE_OK; 143344961713Sgirish 14342e59129aSraghus if (NXGE_IS_VALID_NEPTUNE_TYPE(nxgep)) { 1435a3c5bd6dSspeer /* determine whether to do TCAM or Hash flow */ 143644961713Sgirish insert_hash = nxge_flow_need_hash_lookup(nxgep, flow_res); 143744961713Sgirish } 143844961713Sgirish if (insert_hash) { 143944961713Sgirish status = nxge_add_fcram_entry(nxgep, flow_res); 144044961713Sgirish } else { 144144961713Sgirish status = nxge_add_tcam_entry(nxgep, flow_res); 144244961713Sgirish } 144344961713Sgirish return (status); 144444961713Sgirish } 144544961713Sgirish 144644961713Sgirish void 144744961713Sgirish nxge_put_tcam(p_nxge_t nxgep, p_mblk_t mp) 144844961713Sgirish { 144944961713Sgirish flow_resource_t *fs; 145044961713Sgirish 1451a3c5bd6dSspeer fs = (flow_resource_t *)mp->b_rptr; 145244961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1453*52ccf843Smisaki "nxge_put_tcam addr fs $%p type %x offset %x", 1454*52ccf843Smisaki fs, fs->flow_spec.flow_type, fs->channel_cookie)); 145544961713Sgirish (void) nxge_add_tcam_entry(nxgep, fs); 145644961713Sgirish } 145744961713Sgirish 145844961713Sgirish nxge_status_t 145944961713Sgirish nxge_fflp_config_tcam_enable(p_nxge_t nxgep) 146044961713Sgirish { 146144961713Sgirish npi_handle_t handle = nxgep->npi_reg_handle; 146244961713Sgirish npi_status_t rs = NPI_SUCCESS; 146344961713Sgirish 146444961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, " ==> nxge_fflp_config_tcam_enable")); 146544961713Sgirish rs = npi_fflp_cfg_tcam_enable(handle); 146644961713Sgirish if (rs & NPI_FFLP_ERROR) { 146744961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1468*52ccf843Smisaki " nxge_fflp_config_tcam_enable failed")); 146944961713Sgirish return (NXGE_ERROR | rs); 147044961713Sgirish } 147144961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, " <== nxge_fflp_config_tcam_enable")); 147244961713Sgirish return (NXGE_OK); 147344961713Sgirish } 147444961713Sgirish 147544961713Sgirish nxge_status_t 147644961713Sgirish nxge_fflp_config_tcam_disable(p_nxge_t nxgep) 147744961713Sgirish { 147844961713Sgirish npi_handle_t handle = nxgep->npi_reg_handle; 147944961713Sgirish npi_status_t rs = NPI_SUCCESS; 148044961713Sgirish 148144961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1482*52ccf843Smisaki " ==> nxge_fflp_config_tcam_disable")); 148344961713Sgirish rs = npi_fflp_cfg_tcam_disable(handle); 148444961713Sgirish if (rs & NPI_FFLP_ERROR) { 148544961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1486*52ccf843Smisaki " nxge_fflp_config_tcam_disable failed")); 148744961713Sgirish return (NXGE_ERROR | rs); 148844961713Sgirish } 148944961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1490*52ccf843Smisaki " <== nxge_fflp_config_tcam_disable")); 149144961713Sgirish return (NXGE_OK); 149244961713Sgirish } 149344961713Sgirish 149444961713Sgirish nxge_status_t 149544961713Sgirish nxge_fflp_config_hash_lookup_enable(p_nxge_t nxgep) 149644961713Sgirish { 149744961713Sgirish npi_handle_t handle = nxgep->npi_reg_handle; 149844961713Sgirish npi_status_t rs = NPI_SUCCESS; 1499a3c5bd6dSspeer p_nxge_dma_pt_cfg_t p_dma_cfgp; 1500a3c5bd6dSspeer p_nxge_hw_pt_cfg_t p_cfgp; 1501a3c5bd6dSspeer uint8_t partition; 150244961713Sgirish 150344961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1504*52ccf843Smisaki " ==> nxge_fflp_config_hash_lookup_enable")); 150544961713Sgirish p_dma_cfgp = (p_nxge_dma_pt_cfg_t)&nxgep->pt_config; 150644961713Sgirish p_cfgp = (p_nxge_hw_pt_cfg_t)&p_dma_cfgp->hw_config; 150744961713Sgirish 1508678453a8Sspeer for (partition = 0; partition < NXGE_MAX_RDC_GROUPS; partition++) { 1509678453a8Sspeer if (p_cfgp->grpids[partition]) { 1510678453a8Sspeer rs = npi_fflp_cfg_fcram_partition_enable( 1511*52ccf843Smisaki handle, partition); 1512678453a8Sspeer if (rs != NPI_SUCCESS) { 1513678453a8Sspeer NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1514678453a8Sspeer " nxge_fflp_config_hash_lookup_enable" 1515678453a8Sspeer "failed FCRAM partition" 1516678453a8Sspeer " enable for partition %d ", partition)); 1517678453a8Sspeer return (NXGE_ERROR | rs); 1518678453a8Sspeer } 151944961713Sgirish } 152044961713Sgirish } 152144961713Sgirish 152244961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1523*52ccf843Smisaki " <== nxge_fflp_config_hash_lookup_enable")); 152444961713Sgirish return (NXGE_OK); 152544961713Sgirish } 152644961713Sgirish 152744961713Sgirish nxge_status_t 152844961713Sgirish nxge_fflp_config_hash_lookup_disable(p_nxge_t nxgep) 152944961713Sgirish { 153044961713Sgirish npi_handle_t handle = nxgep->npi_reg_handle; 153144961713Sgirish npi_status_t rs = NPI_SUCCESS; 1532a3c5bd6dSspeer p_nxge_dma_pt_cfg_t p_dma_cfgp; 1533a3c5bd6dSspeer p_nxge_hw_pt_cfg_t p_cfgp; 1534a3c5bd6dSspeer uint8_t partition; 153544961713Sgirish 153644961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1537*52ccf843Smisaki " ==> nxge_fflp_config_hash_lookup_disable")); 153844961713Sgirish p_dma_cfgp = (p_nxge_dma_pt_cfg_t)&nxgep->pt_config; 153944961713Sgirish p_cfgp = (p_nxge_hw_pt_cfg_t)&p_dma_cfgp->hw_config; 154044961713Sgirish 1541678453a8Sspeer for (partition = 0; partition < NXGE_MAX_RDC_GROUPS; partition++) { 1542678453a8Sspeer if (p_cfgp->grpids[partition]) { 1543678453a8Sspeer rs = npi_fflp_cfg_fcram_partition_disable(handle, 1544678453a8Sspeer partition); 1545678453a8Sspeer if (rs != NPI_SUCCESS) { 1546678453a8Sspeer NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1547678453a8Sspeer " nxge_fflp_config_hash_lookup_disable" 1548678453a8Sspeer " failed FCRAM partition" 1549678453a8Sspeer " disable for partition %d ", partition)); 1550678453a8Sspeer return (NXGE_ERROR | rs); 1551678453a8Sspeer } 155244961713Sgirish } 155344961713Sgirish } 155444961713Sgirish 155544961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1556*52ccf843Smisaki " <== nxge_fflp_config_hash_lookup_disable")); 155744961713Sgirish return (NXGE_OK); 155844961713Sgirish } 155944961713Sgirish 156044961713Sgirish nxge_status_t 156144961713Sgirish nxge_fflp_config_llc_snap_enable(p_nxge_t nxgep) 156244961713Sgirish { 156344961713Sgirish npi_handle_t handle = nxgep->npi_reg_handle; 156444961713Sgirish npi_status_t rs = NPI_SUCCESS; 156544961713Sgirish 156644961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1567*52ccf843Smisaki " ==> nxge_fflp_config_llc_snap_enable")); 156844961713Sgirish rs = npi_fflp_cfg_llcsnap_enable(handle); 156944961713Sgirish if (rs & NPI_FFLP_ERROR) { 157044961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1571*52ccf843Smisaki " nxge_fflp_config_llc_snap_enable failed")); 157244961713Sgirish return (NXGE_ERROR | rs); 157344961713Sgirish } 157444961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1575*52ccf843Smisaki " <== nxge_fflp_config_llc_snap_enable")); 157644961713Sgirish return (NXGE_OK); 157744961713Sgirish } 157844961713Sgirish 157944961713Sgirish nxge_status_t 158044961713Sgirish nxge_fflp_config_llc_snap_disable(p_nxge_t nxgep) 158144961713Sgirish { 158244961713Sgirish npi_handle_t handle = nxgep->npi_reg_handle; 158344961713Sgirish npi_status_t rs = NPI_SUCCESS; 1584a3c5bd6dSspeer 158544961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1586*52ccf843Smisaki " ==> nxge_fflp_config_llc_snap_disable")); 158744961713Sgirish rs = npi_fflp_cfg_llcsnap_disable(handle); 158844961713Sgirish if (rs & NPI_FFLP_ERROR) { 158944961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1590*52ccf843Smisaki " nxge_fflp_config_llc_snap_disable failed")); 159144961713Sgirish return (NXGE_ERROR | rs); 159244961713Sgirish } 159344961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1594*52ccf843Smisaki " <== nxge_fflp_config_llc_snap_disable")); 159544961713Sgirish return (NXGE_OK); 159644961713Sgirish } 159744961713Sgirish 159844961713Sgirish nxge_status_t 159944961713Sgirish nxge_fflp_ip_usr_class_config(p_nxge_t nxgep, tcam_class_t class, 1600a3c5bd6dSspeer uint32_t config) 160144961713Sgirish { 160244961713Sgirish npi_status_t rs = NPI_SUCCESS; 160344961713Sgirish npi_handle_t handle = nxgep->npi_reg_handle; 160444961713Sgirish uint8_t tos, tos_mask, proto, ver = 0; 160544961713Sgirish uint8_t class_enable = 0; 160644961713Sgirish 160744961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "==> nxge_fflp_ip_usr_class_config")); 160844961713Sgirish 160944961713Sgirish tos = (config & NXGE_CLASS_CFG_IP_TOS_MASK) >> 1610*52ccf843Smisaki NXGE_CLASS_CFG_IP_TOS_SHIFT; 161144961713Sgirish tos_mask = (config & NXGE_CLASS_CFG_IP_TOS_MASK_MASK) >> 1612*52ccf843Smisaki NXGE_CLASS_CFG_IP_TOS_MASK_SHIFT; 161344961713Sgirish proto = (config & NXGE_CLASS_CFG_IP_PROTO_MASK) >> 1614*52ccf843Smisaki NXGE_CLASS_CFG_IP_PROTO_SHIFT; 161544961713Sgirish if (config & NXGE_CLASS_CFG_IP_IPV6_MASK) 161644961713Sgirish ver = 1; 161744961713Sgirish if (config & NXGE_CLASS_CFG_IP_ENABLE_MASK) 161844961713Sgirish class_enable = 1; 161944961713Sgirish rs = npi_fflp_cfg_ip_usr_cls_set(handle, class, tos, tos_mask, 1620*52ccf843Smisaki proto, ver); 162144961713Sgirish if (rs & NPI_FFLP_ERROR) { 162244961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1623*52ccf843Smisaki " nxge_fflp_ip_usr_class_config" 1624*52ccf843Smisaki " for class %d failed ", class)); 162544961713Sgirish return (NXGE_ERROR | rs); 162644961713Sgirish } 162744961713Sgirish if (class_enable) 162844961713Sgirish rs = npi_fflp_cfg_ip_usr_cls_enable(handle, class); 162944961713Sgirish else 163044961713Sgirish rs = npi_fflp_cfg_ip_usr_cls_disable(handle, class); 163144961713Sgirish 163244961713Sgirish if (rs & NPI_FFLP_ERROR) { 163344961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1634*52ccf843Smisaki " nxge_fflp_ip_usr_class_config" 1635*52ccf843Smisaki " TCAM enable/disable for class %d failed ", class)); 163644961713Sgirish return (NXGE_ERROR | rs); 163744961713Sgirish } 163844961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "<== nxge_fflp_ip_usr_class_config")); 163944961713Sgirish return (NXGE_OK); 164044961713Sgirish } 164144961713Sgirish 164244961713Sgirish nxge_status_t 1643a3c5bd6dSspeer nxge_fflp_ip_class_config(p_nxge_t nxgep, tcam_class_t class, uint32_t config) 164444961713Sgirish { 164544961713Sgirish uint32_t class_config; 164644961713Sgirish nxge_status_t t_status = NXGE_OK; 164744961713Sgirish nxge_status_t f_status = NXGE_OK; 1648a3c5bd6dSspeer p_nxge_class_pt_cfg_t p_class_cfgp; 164944961713Sgirish 165044961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, " ==> nxge_fflp_ip_class_config")); 1651a3c5bd6dSspeer 165244961713Sgirish p_class_cfgp = (p_nxge_class_pt_cfg_t)&nxgep->class_config; 165344961713Sgirish class_config = p_class_cfgp->class_cfg[class]; 165444961713Sgirish 165544961713Sgirish if (class_config != config) { 165644961713Sgirish p_class_cfgp->class_cfg[class] = config; 165744961713Sgirish class_config = config; 165844961713Sgirish } 165944961713Sgirish 166044961713Sgirish t_status = nxge_cfg_tcam_ip_class(nxgep, class, class_config); 166144961713Sgirish f_status = nxge_cfg_ip_cls_flow_key(nxgep, class, class_config); 166244961713Sgirish 166344961713Sgirish if (t_status & NPI_FFLP_ERROR) { 166444961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1665*52ccf843Smisaki " nxge_fflp_ip_class_config %x" 1666*52ccf843Smisaki " for class %d tcam failed", config, class)); 166744961713Sgirish return (t_status); 166844961713Sgirish } 166944961713Sgirish if (f_status & NPI_FFLP_ERROR) { 167044961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1671*52ccf843Smisaki " nxge_fflp_ip_class_config %x" 1672*52ccf843Smisaki " for class %d flow key failed", config, class)); 167344961713Sgirish return (f_status); 167444961713Sgirish } 167544961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "<== nxge_fflp_ip_class_config")); 167644961713Sgirish return (NXGE_OK); 167744961713Sgirish } 167844961713Sgirish 167944961713Sgirish nxge_status_t 168044961713Sgirish nxge_fflp_ip_class_config_get(p_nxge_t nxgep, tcam_class_t class, 1681a3c5bd6dSspeer uint32_t *config) 168244961713Sgirish { 168344961713Sgirish uint32_t t_class_config, f_class_config; 168444961713Sgirish int t_status = NXGE_OK; 168544961713Sgirish int f_status = NXGE_OK; 168644961713Sgirish 168744961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, " ==> nxge_fflp_ip_class_config")); 1688a3c5bd6dSspeer 168944961713Sgirish t_class_config = f_class_config = 0; 169044961713Sgirish t_status = nxge_cfg_tcam_ip_class_get(nxgep, class, &t_class_config); 169144961713Sgirish f_status = nxge_cfg_ip_cls_flow_key_get(nxgep, class, &f_class_config); 169244961713Sgirish 169344961713Sgirish if (t_status & NPI_FFLP_ERROR) { 169444961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1695*52ccf843Smisaki " nxge_fflp_ip_class_config_get " 1696*52ccf843Smisaki " for class %d tcam failed", class)); 169744961713Sgirish return (t_status); 169844961713Sgirish } 169944961713Sgirish 170044961713Sgirish if (f_status & NPI_FFLP_ERROR) { 170144961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1702*52ccf843Smisaki " nxge_fflp_ip_class_config_get " 1703*52ccf843Smisaki " for class %d flow key failed", class)); 170444961713Sgirish return (f_status); 170544961713Sgirish } 170644961713Sgirish 170744961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1708*52ccf843Smisaki " nxge_fflp_ip_class_config tcam %x flow %x", 1709*52ccf843Smisaki t_class_config, f_class_config)); 171044961713Sgirish 171144961713Sgirish *config = t_class_config | f_class_config; 171244961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "<== nxge_fflp_ip_class_config_get")); 171344961713Sgirish return (NXGE_OK); 171444961713Sgirish } 171544961713Sgirish 171644961713Sgirish nxge_status_t 171744961713Sgirish nxge_fflp_ip_class_config_all(p_nxge_t nxgep) 171844961713Sgirish { 171944961713Sgirish uint32_t class_config; 172044961713Sgirish tcam_class_t class; 172144961713Sgirish 172244961713Sgirish #ifdef NXGE_DEBUG 172344961713Sgirish int status = NXGE_OK; 172444961713Sgirish #endif 172544961713Sgirish 172644961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "==> nxge_fflp_ip_class_config")); 172744961713Sgirish for (class = TCAM_CLASS_TCP_IPV4; 1728*52ccf843Smisaki class <= TCAM_CLASS_SCTP_IPV6; class++) { 172944961713Sgirish class_config = nxgep->class_config.class_cfg[class]; 173044961713Sgirish #ifndef NXGE_DEBUG 173144961713Sgirish (void) nxge_fflp_ip_class_config(nxgep, class, class_config); 173244961713Sgirish #else 173344961713Sgirish status = nxge_fflp_ip_class_config(nxgep, class, class_config); 173444961713Sgirish if (status & NPI_FFLP_ERROR) { 173544961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1736*52ccf843Smisaki "nxge_fflp_ip_class_config failed " 1737*52ccf843Smisaki " class %d config %x ", 1738*52ccf843Smisaki class, class_config)); 173944961713Sgirish } 174044961713Sgirish #endif 174144961713Sgirish } 174244961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "<== nxge_fflp_ip_class_config")); 174344961713Sgirish return (NXGE_OK); 174444961713Sgirish } 174544961713Sgirish 174644961713Sgirish nxge_status_t 174744961713Sgirish nxge_fflp_config_vlan_table(p_nxge_t nxgep, uint16_t vlan_id) 174844961713Sgirish { 174944961713Sgirish uint8_t port, rdc_grp; 175044961713Sgirish npi_handle_t handle; 175144961713Sgirish npi_status_t rs = NPI_SUCCESS; 175244961713Sgirish uint8_t priority = 1; 175344961713Sgirish p_nxge_mv_cfg_t vlan_table; 1754a3c5bd6dSspeer p_nxge_class_pt_cfg_t p_class_cfgp; 1755a3c5bd6dSspeer p_nxge_hw_list_t hw_p; 175644961713Sgirish 175744961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "==> nxge_fflp_config_vlan_table")); 175844961713Sgirish p_class_cfgp = (p_nxge_class_pt_cfg_t)&nxgep->class_config; 175944961713Sgirish handle = nxgep->npi_reg_handle; 176044961713Sgirish vlan_table = p_class_cfgp->vlan_tbl; 176144961713Sgirish port = nxgep->function_num; 176244961713Sgirish 176344961713Sgirish if (vlan_table[vlan_id].flag == 0) { 176444961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1765*52ccf843Smisaki " nxge_fflp_config_vlan_table" 1766*52ccf843Smisaki " vlan id is not configured %d", vlan_id)); 176744961713Sgirish return (NXGE_ERROR); 176844961713Sgirish } 176944961713Sgirish 177044961713Sgirish if ((hw_p = nxgep->nxge_hw_p) == NULL) { 177144961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1772*52ccf843Smisaki " nxge_fflp_config_vlan_table:" 1773*52ccf843Smisaki " common hardware not set", nxgep->niu_type)); 177444961713Sgirish return (NXGE_ERROR); 177544961713Sgirish } 177644961713Sgirish MUTEX_ENTER(&hw_p->nxge_vlan_lock); 177744961713Sgirish rdc_grp = vlan_table[vlan_id].rdctbl; 177844961713Sgirish rs = npi_fflp_cfg_enet_vlan_table_assoc(handle, 1779*52ccf843Smisaki port, vlan_id, 1780*52ccf843Smisaki rdc_grp, priority); 178144961713Sgirish 178244961713Sgirish MUTEX_EXIT(&hw_p->nxge_vlan_lock); 178344961713Sgirish if (rs & NPI_FFLP_ERROR) { 178444961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1785*52ccf843Smisaki "nxge_fflp_config_vlan_table failed " 1786*52ccf843Smisaki " Port %d vlan_id %d rdc_grp %d", 1787*52ccf843Smisaki port, vlan_id, rdc_grp)); 178844961713Sgirish return (NXGE_ERROR | rs); 178944961713Sgirish } 1790a3c5bd6dSspeer 179144961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "<== nxge_fflp_config_vlan_table")); 179244961713Sgirish return (NXGE_OK); 179344961713Sgirish } 179444961713Sgirish 179544961713Sgirish nxge_status_t 179644961713Sgirish nxge_fflp_update_hw(p_nxge_t nxgep) 179744961713Sgirish { 179844961713Sgirish nxge_status_t status = NXGE_OK; 179944961713Sgirish p_nxge_param_t pa; 180044961713Sgirish uint64_t cfgd_vlans; 180144961713Sgirish uint64_t *val_ptr; 180244961713Sgirish int i; 180344961713Sgirish int num_macs; 180444961713Sgirish uint8_t alt_mac; 180544961713Sgirish nxge_param_map_t *p_map; 180644961713Sgirish p_nxge_mv_cfg_t vlan_table; 1807a3c5bd6dSspeer p_nxge_class_pt_cfg_t p_class_cfgp; 1808a3c5bd6dSspeer p_nxge_dma_pt_cfg_t p_all_cfgp; 1809a3c5bd6dSspeer p_nxge_hw_pt_cfg_t p_cfgp; 181044961713Sgirish 181144961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "==> nxge_fflp_update_hw")); 1812a3c5bd6dSspeer 181344961713Sgirish p_class_cfgp = (p_nxge_class_pt_cfg_t)&nxgep->class_config; 181444961713Sgirish p_all_cfgp = (p_nxge_dma_pt_cfg_t)&nxgep->pt_config; 181544961713Sgirish p_cfgp = (p_nxge_hw_pt_cfg_t)&p_all_cfgp->hw_config; 181644961713Sgirish 181744961713Sgirish status = nxge_fflp_set_hash1(nxgep, p_class_cfgp->init_h1); 181844961713Sgirish if (status != NXGE_OK) { 181944961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1820*52ccf843Smisaki "nxge_fflp_set_hash1 Failed")); 182144961713Sgirish return (NXGE_ERROR); 182244961713Sgirish } 182344961713Sgirish 182444961713Sgirish status = nxge_fflp_set_hash2(nxgep, p_class_cfgp->init_h2); 182544961713Sgirish if (status != NXGE_OK) { 182644961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1827*52ccf843Smisaki "nxge_fflp_set_hash2 Failed")); 182844961713Sgirish return (NXGE_ERROR); 182944961713Sgirish } 183044961713Sgirish vlan_table = p_class_cfgp->vlan_tbl; 183144961713Sgirish 1832a3c5bd6dSspeer /* configure vlan tables */ 183344961713Sgirish pa = (p_nxge_param_t)&nxgep->param_arr[param_vlan_2rdc_grp]; 1834adfcba55Sjoycey #if defined(__i386) 1835adfcba55Sjoycey val_ptr = (uint64_t *)(uint32_t)pa->value; 1836adfcba55Sjoycey #else 183744961713Sgirish val_ptr = (uint64_t *)pa->value; 1838adfcba55Sjoycey #endif 1839a3c5bd6dSspeer cfgd_vlans = ((pa->type & NXGE_PARAM_ARRAY_CNT_MASK) >> 1840*52ccf843Smisaki NXGE_PARAM_ARRAY_CNT_SHIFT); 184144961713Sgirish 184244961713Sgirish for (i = 0; i < cfgd_vlans; i++) { 184344961713Sgirish p_map = (nxge_param_map_t *)&val_ptr[i]; 184444961713Sgirish if (vlan_table[p_map->param_id].flag) { 184544961713Sgirish status = nxge_fflp_config_vlan_table(nxgep, 1846*52ccf843Smisaki p_map->param_id); 184744961713Sgirish if (status != NXGE_OK) { 184844961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1849*52ccf843Smisaki "nxge_fflp_config_vlan_table Failed")); 185044961713Sgirish return (NXGE_ERROR); 185144961713Sgirish } 185244961713Sgirish } 185344961713Sgirish } 1854a3c5bd6dSspeer 1855a3c5bd6dSspeer /* config MAC addresses */ 185644961713Sgirish num_macs = p_cfgp->max_macs; 185744961713Sgirish pa = (p_nxge_param_t)&nxgep->param_arr[param_mac_2rdc_grp]; 1858adfcba55Sjoycey #if defined(__i386) 1859adfcba55Sjoycey val_ptr = (uint64_t *)(uint32_t)pa->value; 1860adfcba55Sjoycey #else 186144961713Sgirish val_ptr = (uint64_t *)pa->value; 1862adfcba55Sjoycey #endif 186344961713Sgirish 186444961713Sgirish for (alt_mac = 0; alt_mac < num_macs; alt_mac++) { 186544961713Sgirish if (p_class_cfgp->mac_host_info[alt_mac].flag) { 186644961713Sgirish status = nxge_logical_mac_assign_rdc_table(nxgep, 1867*52ccf843Smisaki alt_mac); 186844961713Sgirish if (status != NXGE_OK) { 186944961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1870*52ccf843Smisaki "nxge_logical_mac_assign_rdc_table" 1871*52ccf843Smisaki " Failed")); 187244961713Sgirish return (NXGE_ERROR); 187344961713Sgirish } 187444961713Sgirish } 187544961713Sgirish } 1876a3c5bd6dSspeer 1877a3c5bd6dSspeer /* Config Hash values */ 1878f6485eecSyc /* config classes */ 187944961713Sgirish status = nxge_fflp_ip_class_config_all(nxgep); 188044961713Sgirish if (status != NXGE_OK) { 188144961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1882*52ccf843Smisaki "nxge_fflp_ip_class_config_all Failed")); 188344961713Sgirish return (NXGE_ERROR); 188444961713Sgirish } 188544961713Sgirish return (NXGE_OK); 188644961713Sgirish } 188744961713Sgirish 188844961713Sgirish nxge_status_t 188944961713Sgirish nxge_classify_init_hw(p_nxge_t nxgep) 189044961713Sgirish { 189144961713Sgirish nxge_status_t status = NXGE_OK; 189244961713Sgirish 189344961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "==> nxge_classify_init_hw")); 189444961713Sgirish 189544961713Sgirish if (nxgep->classifier.state & NXGE_FFLP_HW_INIT) { 189644961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, 1897*52ccf843Smisaki "nxge_classify_init_hw already init")); 189844961713Sgirish return (NXGE_OK); 189944961713Sgirish } 190044961713Sgirish 1901a3c5bd6dSspeer /* Now do a real configuration */ 190244961713Sgirish status = nxge_fflp_update_hw(nxgep); 190344961713Sgirish if (status != NXGE_OK) { 190444961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1905*52ccf843Smisaki "nxge_fflp_update_hw failed")); 190644961713Sgirish return (NXGE_ERROR); 190744961713Sgirish } 1908a3c5bd6dSspeer 1909a3c5bd6dSspeer /* Init RDC tables? ? who should do that? rxdma or fflp ? */ 1910a3c5bd6dSspeer /* attach rdc table to the MAC port. */ 191144961713Sgirish status = nxge_main_mac_assign_rdc_table(nxgep); 191244961713Sgirish if (status != NXGE_OK) { 191344961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1914*52ccf843Smisaki "nxge_main_mac_assign_rdc_table failed")); 191544961713Sgirish return (NXGE_ERROR); 191644961713Sgirish } 1917a3c5bd6dSspeer 191858324dfcSspeer status = nxge_alt_mcast_mac_assign_rdc_table(nxgep); 191944961713Sgirish if (status != NXGE_OK) { 192044961713Sgirish NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1921*52ccf843Smisaki "nxge_multicast_mac_assign_rdc_table failed")); 192244961713Sgirish return (NXGE_ERROR); 192344961713Sgirish } 192414ea4bb7Ssd 192514ea4bb7Ssd status = nxge_tcam_handle_ip_fragment(nxgep); 192614ea4bb7Ssd if (status != NXGE_OK) { 192714ea4bb7Ssd NXGE_ERROR_MSG((nxgep, NXGE_ERR_CTL, 1928*52ccf843Smisaki "nxge_tcam_handle_ip_fragment failed")); 192914ea4bb7Ssd return (NXGE_ERROR); 193014ea4bb7Ssd } 193144961713Sgirish 193244961713Sgirish nxgep->classifier.state |= NXGE_FFLP_HW_INIT; 193344961713Sgirish NXGE_DEBUG_MSG((nxgep, FFLP_CTL, "<== nxge_classify_init_hw")); 193444961713Sgirish return (NXGE_OK); 193544961713Sgirish } 193644961713Sgirish 193744961713Sgirish nxge_status_t 193844961713Sgirish nxge_fflp_handle_sys_errors(p_nxge_t nxgep) 193944961713Sgirish { 1940a3c5bd6dSspeer npi_handle_t handle; 1941a3c5bd6dSspeer p_nxge_fflp_stats_t statsp; 1942a3c5bd6dSspeer uint8_t portn, rdc_grp; 1943a3c5bd6dSspeer p_nxge_dma_pt_cfg_t p_dma_cfgp; 1944a3c5bd6dSspeer p_nxge_hw_pt_cfg_t p_cfgp; 1945a3c5bd6dSspeer vlan_par_err_t vlan_err; 1946a3c5bd6dSspeer tcam_err_t tcam_err; 1947a3c5bd6dSspeer hash_lookup_err_log1_t fcram1_err; 1948a3c5bd6dSspeer hash_lookup_err_log2_t fcram2_err; 1949a3c5bd6dSspeer hash_tbl_data_log_t fcram_err; 195044961713Sgirish 195144961713Sgirish handle = nxgep->npi_handle; 195244961713Sgirish statsp = (p_nxge_fflp_stats_t)&nxgep->statsp->fflp_stats; 195344961713Sgirish portn = nxgep->mac.portnum; 195444961713Sgirish 195544961713Sgirish /* 1956a3c5bd6dSspeer * need to read the fflp error registers to figure out what the error 1957a3c5bd6dSspeer * is 195844961713Sgirish */ 195944961713Sgirish npi_fflp_vlan_error_get(handle, &vlan_err); 196044961713Sgirish npi_fflp_tcam_error_get(handle, &tcam_err); 196144961713Sgirish 196244961713Sgirish if (vlan_err.bits.ldw.m_err || vlan_err.bits.ldw.err) { 196344961713Sgirish NXGE_ERROR_MSG((nxgep, FFLP_CTL, 1964*52ccf843Smisaki " vlan table parity error on port %d" 1965*52ccf843Smisaki " addr: 0x%x data: 0x%x", 1966*52ccf843Smisaki portn, vlan_err.bits.ldw.addr, 1967*52ccf843Smisaki vlan_err.bits.ldw.data)); 196844961713Sgirish statsp->vlan_parity_err++; 196944961713Sgirish 197044961713Sgirish if (vlan_err.bits.ldw.m_err) { 197144961713Sgirish NXGE_ERROR_MSG((nxgep, FFLP_CTL, 1972*52ccf843Smisaki " vlan table multiple errors on port %d", 1973*52ccf843Smisaki portn)); 197444961713Sgirish } 197544961713Sgirish statsp->errlog.vlan = (uint32_t)vlan_err.value; 197644961713Sgirish NXGE_FM_REPORT_ERROR(nxgep, NULL, NULL, 1977*52ccf843Smisaki NXGE_FM_EREPORT_FFLP_VLAN_PAR_ERR); 197844961713Sgirish npi_fflp_vlan_error_clear(handle); 197944961713Sgirish } 198044961713Sgirish 198144961713Sgirish if (tcam_err.bits.ldw.err) { 198244961713Sgirish if (tcam_err.bits.ldw.p_ecc != 0) { 198344961713Sgirish NXGE_ERROR_MSG((nxgep, FFLP_CTL, 1984*52ccf843Smisaki " TCAM ECC error on port %d" 1985*52ccf843Smisaki " TCAM entry: 0x%x syndrome: 0x%x", 1986*52ccf843Smisaki portn, tcam_err.bits.ldw.addr, 1987*52ccf843Smisaki tcam_err.bits.ldw.syndrome)); 198844961713Sgirish statsp->tcam_ecc_err++; 198944961713Sgirish } else { 199044961713Sgirish NXGE_ERROR_MSG((nxgep, FFLP_CTL, 1991*52ccf843Smisaki " TCAM Parity error on port %d" 1992*52ccf843Smisaki " addr: 0x%x parity value: 0x%x", 1993*52ccf843Smisaki portn, tcam_err.bits.ldw.addr, 1994*52ccf843Smisaki tcam_err.bits.ldw.syndrome)); 199544961713Sgirish statsp->tcam_parity_err++; 199644961713Sgirish } 199744961713Sgirish 199844961713Sgirish if (tcam_err.bits.ldw.mult) { 199944961713Sgirish NXGE_ERROR_MSG((nxgep, FFLP_CTL, 2000*52ccf843Smisaki " TCAM Multiple errors on port %d", portn)); 200144961713Sgirish } else { 200244961713Sgirish NXGE_ERROR_MSG((nxgep, FFLP_CTL, 2003*52ccf843Smisaki " TCAM PIO error on port %d", portn)); 200444961713Sgirish } 200544961713Sgirish 200644961713Sgirish statsp->errlog.tcam = (uint32_t)tcam_err.value; 200744961713Sgirish NXGE_FM_REPORT_ERROR(nxgep, NULL, NULL, 2008*52ccf843Smisaki NXGE_FM_EREPORT_FFLP_TCAM_ERR); 200944961713Sgirish npi_fflp_tcam_error_clear(handle); 201044961713Sgirish } 201144961713Sgirish 201244961713Sgirish p_dma_cfgp = (p_nxge_dma_pt_cfg_t)&nxgep->pt_config; 201344961713Sgirish p_cfgp = (p_nxge_hw_pt_cfg_t)&p_dma_cfgp->hw_config; 201444961713Sgirish 2015678453a8Sspeer for (rdc_grp = 0; rdc_grp < NXGE_MAX_RDC_GROUPS; rdc_grp++) { 2016678453a8Sspeer if (p_cfgp->grpids[rdc_grp]) { 2017678453a8Sspeer npi_fflp_fcram_error_get(handle, &fcram_err, rdc_grp); 2018678453a8Sspeer if (fcram_err.bits.ldw.pio_err) { 2019678453a8Sspeer NXGE_ERROR_MSG((nxgep, FFLP_CTL, 2020*52ccf843Smisaki " FCRAM PIO ECC error on port %d" 2021*52ccf843Smisaki " rdc group: %d Hash Table addr: 0x%x" 2022*52ccf843Smisaki " syndrome: 0x%x", 2023*52ccf843Smisaki portn, rdc_grp, 2024*52ccf843Smisaki fcram_err.bits.ldw.fcram_addr, 2025*52ccf843Smisaki fcram_err.bits.ldw.syndrome)); 2026678453a8Sspeer statsp->hash_pio_err[rdc_grp]++; 2027678453a8Sspeer statsp->errlog.hash_pio[rdc_grp] = 2028678453a8Sspeer (uint32_t)fcram_err.value; 2029678453a8Sspeer NXGE_FM_REPORT_ERROR(nxgep, NULL, NULL, 2030678453a8Sspeer NXGE_FM_EREPORT_FFLP_HASHT_DATA_ERR); 2031678453a8Sspeer npi_fflp_fcram_error_clear(handle, rdc_grp); 2032678453a8Sspeer } 203344961713Sgirish } 203444961713Sgirish } 203544961713Sgirish 203644961713Sgirish npi_fflp_fcram_error_log1_get(handle, &fcram1_err); 203744961713Sgirish if (fcram1_err.bits.ldw.ecc_err) { 203844961713Sgirish char *multi_str = ""; 203944961713Sgirish char *multi_bit_str = ""; 2040a3c5bd6dSspeer 204144961713Sgirish npi_fflp_fcram_error_log2_get(handle, &fcram2_err); 204244961713Sgirish if (fcram1_err.bits.ldw.mult_lk) { 204344961713Sgirish multi_str = "multiple"; 204444961713Sgirish } 204544961713Sgirish if (fcram1_err.bits.ldw.mult_bit) { 204644961713Sgirish multi_bit_str = "multiple bits"; 204744961713Sgirish } 2048f6485eecSyc statsp->hash_lookup_err++; 204944961713Sgirish NXGE_ERROR_MSG((nxgep, FFLP_CTL, 2050*52ccf843Smisaki " FCRAM %s lookup %s ECC error on port %d" 2051*52ccf843Smisaki " H1: 0x%x Subarea: 0x%x Syndrome: 0x%x", 2052*52ccf843Smisaki multi_str, multi_bit_str, portn, 2053*52ccf843Smisaki fcram2_err.bits.ldw.h1, 2054*52ccf843Smisaki fcram2_err.bits.ldw.subarea, 2055*52ccf843Smisaki fcram2_err.bits.ldw.syndrome)); 205644961713Sgirish NXGE_FM_REPORT_ERROR(nxgep, NULL, NULL, 2057*52ccf843Smisaki NXGE_FM_EREPORT_FFLP_HASHT_LOOKUP_ERR); 205844961713Sgirish } 205944961713Sgirish statsp->errlog.hash_lookup1 = (uint32_t)fcram1_err.value; 206044961713Sgirish statsp->errlog.hash_lookup2 = (uint32_t)fcram2_err.value; 206144961713Sgirish return (NXGE_OK); 206244961713Sgirish } 2063